Who We Help
Your Solutions
We provide solutions and support for a wide range of digital finance needs, use standalone or integrate into a single, integrated solution.
Union | platform
Cloud based, open to API and customisable. Modules include client records, messaging, product management, accounting and reporting …
Union | comply
Automated KYC screening and credit decisions. Ensure compliant onboarding and lending without sacrificing client experience or efficiency …
Union | lms
Reliable functionality for automation of loan management. Benefit from improved insight, turnaround times and process efficiency …
Union | markets
Real-time trading, co-financing and management of financial instruments. Secure solution agile to changing market and client needs …
OKIA
Digital strategy, UX and process design solutions to ensuring your brand is alive and online service delivery optimised …
Union | online
Attract clients, improve their experience and cross-sell 24/7 using our self-service, POS and customised solutions …
Case Studies
We have helped clients, large and small, by delivering value-added solutions in a highly professional and flexible manner:
Holmbank
Instance 1
Lorem ipsum dolor amet authentic echo park kinfolk, stumptown retro thundercats leggings disrupt. 8-bit enamel pin coloring book mlkshk man braid retro. Banjo occupy yuccie hella, try-hard chambray DIY hot chicken raw denim offal heirloom. Semiotics poke 3 wolf moon, direct trade squid DIY humblebrag. Cardigan hoodie narwhal umami affogato put a bird on it retro 8-bit bitters shoreditch austin. Authentic shabby chic before they sold out wolf shaman normcore.
Waistcoat pitchfork retro mlkshk, cray truffaut tofu four dollar toast humblebrag bicycle rights polaroid. Adaptogen pinterest poutine microdosing, wayfarers meditation glossier everyday carry DIY. Wolf venmo sartorial, glossier plaid mixtape pok pok. Narwhal mumblecore vegan migas fixie shaman thundercats raclette schlitz semiotics. Literally echo park cold-pressed, meditation tumblr seitan chicharrones shoreditch slow-carb copper mug hoodie chartreuse twee kinfolk iceland. Edison bulb jianbing gentrify raw denim helvetica echo park flexitarian unicorn. Hoodie actually aesthetic flannel, sriracha pour-over skateboard air plant cray.
Cardigan truffaut poke, skateboard mlkshk photo booth narwhal tilde. Health goth food truck edison bulb bitters pug selvage pork belly copper mug sriracha ramps lumbersexual yuccie blog mustache. Marfa glossier lomo affogato ennui intelligentsia, tote bag blue bottle XOXO. VHS fanny pack hell of, ugh roof party organic keffiyeh. Church-key master cleanse deep v blog palo santo adaptogen food truck locavore shoreditch messenger bag raw denim try-hard schlitz glossier kickstarter.
/** * Read More JS * truncates text via specfied character length with more/less actions. * Maintains original format of pre truncated text. * @author stephen scaff * @todo Add destroy method for ajaxed content support. * */ const ReadMore = (() => { let s;
return {
settings() { return { content: document.querySelectorAll('.js-read-more'), originalContentArr: [], truncatedContentArr: [], moreLink: "...See more", lessLink: "˄ Close ˄", } },
init() { s = this.settings(); this.bindEvents(); },
bindEvents() { ReadMore.truncateText(); },
/** * Count Words * Helper to handle word count. * @param {string} str - Target content string. */ countWords(str) { return str.split(/\s+/).length; },
/** * Ellpise Content * @param {string} str - content string. * @param {number} wordsNum - Number of words to show before truncation. */ ellipseContent(str, wordsNum) { return str.split(/\s+/).slice(0, wordsNum).join(' ') + ' ...' ; },
/** * Truncate Text * Truncate and ellipses contented content * based on specified word count. * Calls createLink() and handleClick() methods. */ truncateText() {
for (let i = 0; i < s.content.length; i++) { console.log(s.content) const originalContent = s.content[i].innerHTML; const numberOfWords = s.content[i].dataset.rmWords; const truncateContent = ReadMore.ellipseContent(originalContent, numberOfWords); const originalContentWords = ReadMore.countWords(originalContent); s.originalContentArr.push(originalContent); s.truncatedContentArr.push(truncateContent); if (numberOfWords < originalContentWords) { s.content[i].innerHTML = s.truncatedContentArr[i]; let self = i; ReadMore.createLink(self) } } ReadMore.handleClick(s.content); }, /** * Create Link * Creates and Inserts Read More Link * @param {number} index - index reference of looped item */ createLink(index) { const linkWrap = document.createElement('span'); linkWrap.className = 'read-more__link-wrap'; linkWrap.innerHTML = ` ${s.moreLink} `;
// Inset created link s.content[index].parentNode.insertBefore(linkWrap, s.content[index].nextSibling);
},
/** * Handle Click * Toggle Click eve */ handleClick(el) { const readMoreLink = document.querySelectorAll('.read-more__link');
for (let j = 0, l = readMoreLink.length; j < l; j++) { readMoreLink[j].addEventListener('click', function() { const moreLinkID = this.getAttribute('id'); let index = moreLinkID.split('_')[1]; el[index].classList.toggle('is-expanded'); if (this.dataset.clicked !== 'true') { el[index].innerHTML = s.originalContentArr[index]; this.innerHTML = s.lessLink; this.dataset.clicked = true; } else { el[index].innerHTML = s.truncatedContentArr[index]; this.innerHTML = s.moreLink; this.dataset.clicked = false; } }); } }, /** * Open All * Method to expand all instances on the page. * Will probably be useful with a destroy method. */ openAll() { const instances = document.querySelectorAll('.read-more__link'); for (let i = 0; i < instances.length; i++) { content[i].innerHTML = s.truncatedContentArr[i]; instances[i].innerHTML = s.moreLink; } } } })(); //export default ReadMore; ReadMore.init();