Skip to content
Merged
Show file tree
Hide file tree
Changes from 13 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 6 additions & 1 deletion apps/juxtaposition-ui/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,8 @@
"lint": "eslint .",
"lint:fix": "eslint . --fix",
"build": "tsup && tsc --noEmit",
"start": "node --enable-source-maps dist/server.js"
"start": "node --enable-source-maps dist/server.js",
"build:sprites": "node scripts/sprites.ts"
},
"dependencies": {
"@aws-sdk/client-s3": "^3.958.0",
Expand Down Expand Up @@ -62,15 +63,19 @@
"@types/node": "^22.19.1",
"@types/react": "^19.1.13",
"@types/react-dom": "^19.2.3",
"@types/spritesmith": "^3.4.5",
"browserslist": "^4.28.0",
"browserslist-to-esbuild": "^2.1.1",
"ejs-lint": "^2.0.1",
"esbuild-fix-imports-plugin": "^1.0.23",
"esbuild-raw-plugin": "^0.3.1",
"eslint": "^9.39.1",
"globals": "^16.5.0",
"handlebars": "^4.7.8",
"nodemon": "^3.1.11",
"npm-run-all": "^4.1.5",
"pixelsmith": "^2.6.0",
"spritesmith": "^3.5.1",
"tsup": "^8.5.1",
"typescript": "^5.9.3"
}
Expand Down
51 changes: 51 additions & 0 deletions apps/juxtaposition-ui/scripts/sprites.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
// Load in dependencies
import { readdirSync, writeFileSync } from 'node:fs';
import { basename } from 'node:path';
import Spritesmith from 'spritesmith';
import handlebars from 'handlebars';

const ctr = 'src/webfiles/ctr';
const ctr_images = ctr + '/images';
const esbuild_ctr = '@/webfiles/ctr';
const sprite_paths = readdirSync(ctr_images + '/sprites')
.filter(path => path.endsWith('.png'))
.map(path => ctr_images + '/sprites/' + path);

// Generate our spritesheet
Spritesmith.run({
src: sprite_paths
}, function handleResult(err, result) {
if (err) {
console.error(err);
return;
}
const { coordinates, image } = result;

const sprites = Object.entries(coordinates).map(([name, coords]) => {
return {
name: basename(name, '.png').replaceAll('_', ':'),
...coords
};
});

// make the css
const res = handlebars.compile(`
/* This file is generated by scripts/sprites.ts */
.sprite {
background-image: url(${esbuild_ctr}/images/sprites.png);
}
{{#each sprites}}
.sprite.sp-{{name}} {
background-position: -{{x}}px -{{y}}px;
width: {{width}}px;
height: {{height}}px;
}
{{/each}}
`)({ sprites });

writeFileSync(ctr + '/css/sprites.css', res, {
encoding: 'utf-8'
});
writeFileSync(ctr + '/images/sprites.png', image);
console.info(`success: wrote ${sprite_paths.length} sprites`);
});
Original file line number Diff line number Diff line change
Expand Up @@ -7,38 +7,38 @@ const empathies = [
value: 0,
miiFaceFile: 'normal_face.png',
sound: 'SE_WAVE_MII_FACE_00',
className: 'feeling-button-normal',
className: 'sprite sp-feeling-normal',
isDefault: true
},
{
value: 1,
miiFaceFile: 'smile_open_mouth.png',
sound: 'SE_WAVE_MII_FACE_01',
className: 'feeling-button-happy'
className: 'sprite sp-feeling-happy'
},
{
value: 2,
miiFaceFile: 'wink_left.png',
sound: 'SE_WAVE_MII_FACE_02',
className: 'feeling-button-like'
className: 'sprite sp-feeling-like'
},
{
value: 3,
miiFaceFile: 'surprise_open_mouth.png',
sound: 'SE_WAVE_MII_FACE_03',
className: 'feeling-button-surprised'
className: 'sprite sp-feeling-surprise'
},
{
value: 4,
miiFaceFile: 'frustrated.png',
sound: 'SE_WAVE_MII_FACE_04',
className: 'feeling-button-frustrated'
className: 'sprite sp-feeling-frustrated'
},
{
value: 5,
miiFaceFile: 'sorrow.png',
sound: 'SE_WAVE_MII_FACE_05',
className: 'feeling-button-puzzled'
className: 'sprite sp-feeling-puzzled'
}
];

Expand Down Expand Up @@ -83,14 +83,14 @@ export function CtrNewPostView(props: NewPostViewProps): ReactNode {
data-sound="SE_WAVE_BALLOON_OPEN"
evt-click="window.alert('Screenshots are not ready yet. Check back soon!')"
>
<img className="preview-image sprite" src="" />
<img className="sprite sp-screenshot" src="" />
</button>
<input id="screenshot-value" type="hidden" name="screenshot" value="" />
</div>
<div className="textarea-container textarea-with-menu active-text">
<menu className="textarea-menu">
<li className="textarea-menu-text">
<span className="sprite text-input selected" id="text-sprite"></span>
<span className="sprite sp-text-input selected" id="text-sprite"></span>
<input
type="radio"
name="_post_type"
Expand All @@ -110,7 +110,7 @@ export function CtrNewPostView(props: NewPostViewProps): ReactNode {
</textarea>
</li>
<li className="textarea-menu-memo">
<span className="sprite memo" id="memo-sprite"></span>
<span className="sprite sp-memo-input" id="memo-sprite"></span>
<input
type="radio"
name="_post_type"
Expand Down
12 changes: 8 additions & 4 deletions apps/juxtaposition-ui/src/services/juxt-web/views/ctr/post.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ export function CtrPostView(props: PostViewProps): ReactNode {
? (
<a href={utils.url('/topics', { topic_tag: post.topic_tag })} data-pjax="#body">
<span>
<span className="sprite tag"></span>
<span className="sprite sp-tag inline-sprite"></span>
<span className="tags">{post.topic_tag}</span>
</span>
</a>
Expand Down Expand Up @@ -92,14 +92,18 @@ export function CtrPostView(props: PostViewProps): ReactNode {
})}
data-post={post.id}
>
<span className="sprite yeah"></span>
<span className="sprite sp-yeah inline-sprite"></span>
</button>
<a href={`/posts/${post.id}`} className="to-permalink-button" data-pjax="#body">
<span className="sprite feeling" id={`count-${post.id}`}>{post.empathy_count}</span>
<span className="sprite sp-yeah-small inline-sprite"></span>
<span className="yeah-count" id={`count-${post.id}`}>{post.empathy_count}</span>
{' '}
{!props.isReply
? (
<span className="sprite reply">{post.reply_count}</span>
<>
<span className="sprite sp-reply inline-sprite"></span>
<span className="reply-count">{post.reply_count}</span>
</>
)
: null}
</a>
Expand Down
8 changes: 4 additions & 4 deletions apps/juxtaposition-ui/src/webfiles/ctr/community.ejs
Original file line number Diff line number Diff line change
Expand Up @@ -20,11 +20,11 @@
</span>
<span class="text">
<span>
<span class="sprite posts"></span>
<%= bundle.numPosts %>
<span class="sprite sp-post-count inline-sprite"></span>
<span id="post-count"><%= bundle.numPosts %></span>
</span>
<span>|
<span class="sprite followers"></span>
<span class="sprite sp-follower-count inline-sprite"></span>
<span id="followers"><%= community.followers %></span>
</span>
</span>
Expand All @@ -45,7 +45,7 @@
<%}%>
<%if(community.permissions.open){%>
<button type="button" class="submit follow yeah-button <%if(children) {%>suggested<%}%> <%if(userContent.followed_communities.indexOf(community.olive_community_id) !== -1){ %>selected<%}%>" onclick="follow(this)" data-sound="SE_WAVE_CHECKBOX_UNCHECK" data-url="/titles/follow" data-community-id="<%= community.olive_community_id %>">
<span class="sprite yeah"></span>
<span class="sprite sp-yeah inline-sprite"></span>
</button>
<%}%>
</header>
Expand Down
163 changes: 39 additions & 124 deletions apps/juxtaposition-ui/src/webfiles/ctr/css/juxt.css

Large diffs are not rendered by default.

126 changes: 126 additions & 0 deletions apps/juxtaposition-ui/src/webfiles/ctr/css/sprites.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,126 @@

/* This file is generated by scripts/sprites.ts */
.sprite {
background-image: url(@/webfiles/ctr/images/sprites.png);
}
.sprite.sp-feeling-frustrated {
background-position: -0px -0px;
width: 28px;
height: 28px;
}
.sprite.sp-feeling-frustrated:checked {
background-position: -28px -0px;
width: 28px;
height: 28px;
}
.sprite.sp-feeling-happy {
background-position: -0px -28px;
width: 28px;
height: 28px;
}
.sprite.sp-feeling-happy:checked {
background-position: -28px -28px;
width: 28px;
height: 28px;
}
.sprite.sp-feeling-like {
background-position: -56px -0px;
width: 28px;
height: 28px;
}
.sprite.sp-feeling-like:checked {
background-position: -56px -28px;
width: 28px;
height: 28px;
}
.sprite.sp-feeling-normal {
background-position: -0px -56px;
width: 28px;
height: 28px;
}
.sprite.sp-feeling-normal:checked {
background-position: -28px -56px;
width: 28px;
height: 28px;
}
.sprite.sp-feeling-puzzled {
background-position: -56px -56px;
width: 28px;
height: 28px;
}
.sprite.sp-feeling-puzzled:checked {
background-position: -84px -0px;
width: 28px;
height: 28px;
}
.sprite.sp-feeling-surprise {
background-position: -84px -28px;
width: 28px;
height: 28px;
}
.sprite.sp-feeling-surprise:checked {
background-position: -84px -56px;
width: 28px;
height: 28px;
}
.sprite.sp-follower-count {
background-position: -112px -72px;
width: 19px;
height: 14px;
}
.sprite.sp-memo-input {
background-position: -112px -38px;
width: 17px;
height: 17px;
}
.sprite.sp-memo-input.selected {
background-position: -112px -55px;
width: 17px;
height: 17px;
}
.sprite.sp-post-count {
background-position: -112px -86px;
width: 16px;
height: 16px;
}
.sprite.sp-reply {
background-position: -78px -84px;
width: 16px;
height: 16px;
}
.sprite.sp-screenshot {
background-position: -0px -84px;
width: 26px;
height: 22px;
}
.sprite.sp-tag {
background-position: -0px -106px;
width: 12px;
height: 12px;
}
.sprite.sp-text-input {
background-position: -26px -84px;
width: 26px;
height: 17px;
}
.sprite.sp-text-input.selected {
background-position: -52px -84px;
width: 26px;
height: 17px;
}
.sprite.sp-yeah-small {
background-position: -94px -84px;
width: 16px;
height: 16px;
}
.sprite.sp-yeah {
background-position: -112px -0px;
width: 20px;
height: 19px;
}
.sprite.sp-yeah.selected {
background-position: -112px -19px;
width: 20px;
height: 19px;
}

Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file not shown.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions apps/juxtaposition-ui/src/webfiles/ctr/js/juxt.js
Original file line number Diff line number Diff line change
Expand Up @@ -129,20 +129,23 @@ function initYeah() {
}
function yeah(e) {
var el = e.currentTarget;
var sprite = el.querySelector('.sprite.sp-yeah');
var id = el.getAttribute('data-post');
var parent = document.getElementById(id);
var count = document.getElementById('count-' + id);
el.disabled = true;
var params = 'postID=' + id;
if (classList.contains(el, 'selected')) {
classList.remove(el, 'selected');
classList.remove(sprite, 'selected');
classList.remove(parent, 'yeah');
if (count) {
count.innerText -= 1;
}
cave.snd_playSe('SE_OLV_CANCEL');
} else {
classList.add(el, 'selected');
classList.add(sprite, 'selected');
classList.add(parent, 'yeah');
if (count) {
count.innerText = ++count.innerText;
Expand Down
Loading