Skip to content

Commit 0456825

Browse files
authored
Merge pull request #753 from ZenUml/feat/fullscreen-rendering
Feat/fullscreen rendering
2 parents 3bdb39e + 7350f41 commit 0456825

File tree

3 files changed

+78
-166
lines changed

3 files changed

+78
-166
lines changed

.github/workflows/deploy-staging.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ jobs:
2626
if: github.actor != 'dependabot[bot]' && github.actor != 'dependabot-preview[bot]' # This conditional will skip the step for Dependabot PRs
2727
run: yarn deploy:staging --token ${{ secrets.FIREBASE_TOKEN }}
2828
- name: Upload artifacts # Find artifacts under actions/jobs
29-
uses: actions/upload-artifact@v3
29+
uses: actions/upload-artifact@v4
3030
with:
3131
name: chrome-extension
3232
path: extension

src/components/ContentWrap.jsx

Lines changed: 74 additions & 165 deletions
Original file line numberDiff line numberDiff line change
@@ -428,9 +428,9 @@ export default class ContentWrap extends Component {
428428
this.props.onLogin();
429429
return;
430430
}
431-
const png = await this.getPngBlob();
432-
saveAs(png, 'zenuml.png');
433-
mixpanel.track({ event: 'downloadPng', category: 'ui' });
431+
const png = await this.getPngBlob();
432+
saveAs(png, 'zenuml.png');
433+
mixpanel.track({ event: 'downloadPng', category: 'ui' });
434434
}
435435

436436
async getPngBlob() {
@@ -817,6 +817,47 @@ export default class ContentWrap extends Component {
817817
this.cm.js.setValue(codeService.addCode(code, param));
818818
}
819819

820+
async toggleFullscreen() {
821+
const demoElement = document.getElementById('js-demo-side');
822+
if (!document.fullscreenElement) {
823+
if (demoElement.requestFullscreen) {
824+
demoElement.requestFullscreen();
825+
trackEvent('ui', 'enterFullscreen');
826+
mixpanel.track('Enter Fullscreen');
827+
} else if (demoElement.mozRequestFullScreen) { /* Firefox */
828+
demoElement.mozRequestFullScreen();
829+
trackEvent('ui', 'enterFullscreen');
830+
mixpanel.track('Enter Fullscreen');
831+
} else if (demoElement.webkitRequestFullscreen) { /* Chrome, Safari & Opera */
832+
demoElement.webkitRequestFullscreen();
833+
trackEvent('ui', 'enterFullscreen');
834+
mixpanel.track('Enter Fullscreen');
835+
} else if (demoElement.msRequestFullscreen) { /* IE/Edge */
836+
demoElement.msRequestFullscreen();
837+
trackEvent('ui', 'enterFullscreen');
838+
mixpanel.track('Enter Fullscreen');
839+
}
840+
} else {
841+
if (document.exitFullscreen) {
842+
document.exitFullscreen();
843+
trackEvent('ui', 'exitFullscreen');
844+
mixpanel.track('Exit Fullscreen');
845+
} else if (document.mozCancelFullScreen) { /* Firefox */
846+
document.mozCancelFullScreen();
847+
trackEvent('ui', 'exitFullscreen');
848+
mixpanel.track('Exit Fullscreen');
849+
} else if (document.webkitExitFullscreen) { /* Chrome, Safari and Opera */
850+
document.webkitExitFullscreen();
851+
trackEvent('ui', 'exitFullscreen');
852+
mixpanel.track('Exit Fullscreen');
853+
} else if (document.msExitFullscreen) { /* IE/Edge */
854+
document.msExitFullscreen();
855+
trackEvent('ui', 'exitFullscreen');
856+
mixpanel.track('Exit Fullscreen');
857+
}
858+
}
859+
}
860+
820861
render() {
821862
return (
822863
<SplitPane
@@ -847,35 +888,6 @@ export default class ContentWrap extends Component {
847888
className="code-wrap"
848889
onTransitionEnd={this.updateCodeWrapCollapseStates.bind(this)}
849890
>
850-
{/* <div
851-
className="js-code-wrap__header code-wrap__header"
852-
title="Double click to toggle code pane"
853-
ondblclick={this.codeWrapHeaderDblClickHandler.bind(this)}
854-
>
855-
<label className="btn-group" title="Click to change">
856-
<span className="code-wrap__header-label">ZenUML</span>
857-
<span className="caret" style="display:none" />
858-
<select
859-
data-type="js"
860-
className="js-mode-select hidden-select"
861-
style="display: none"
862-
onChange={this.codeModeChangeHandler.bind(this)}
863-
value={this.props.currentItem.jsMode}
864-
>
865-
<option value="js">JS</option>
866-
<option value="coffee">CoffeeScript</option>
867-
<option value="es6">ES6 (Babel)</option>
868-
<option value="typescript">TypeScript</option>
869-
</select>
870-
</label>
871-
<div className="code-wrap__header-right-options">
872-
<a
873-
className="js-code-collapse-btn code-wrap__header-btn code-wrap__collapse-btn"
874-
title="Toggle code pane"
875-
onClick={this.collapseBtnHandler.bind(this)}
876-
/>
877-
</div>
878-
</div> */}
879891
<Toolbox clickSvg={this.toolboxUpdateToApp.bind(this)} />
880892
<UserCodeMirror
881893
ref={(dslEditor) => (this.dslEditor = dslEditor)}
@@ -950,11 +962,6 @@ export default class ContentWrap extends Component {
950962
<use xlinkHref="#settings-icon" />
951963
</svg>
952964
</a>
953-
{/* <a
954-
className="js-code-collapse-btn code-wrap__header-btn code-wrap__collapse-btn"
955-
title="Toggle code pane"
956-
onClick={this.collapseBtnHandler.bind(this)}
957-
/> */}
958965
</div>
959966
</div>
960967
<UserCodeMirror
@@ -977,117 +984,8 @@ export default class ContentWrap extends Component {
977984
/>
978985
</div>
979986
</div>
980-
{/*<div label="Cheat sheet">*/}
981-
{/* <div*/}
982-
{/* data-code-wrap-id="0"*/}
983-
{/* id="htmlCodeEl"*/}
984-
{/* data-type="html"*/}
985-
{/* class="code-wrap"*/}
986-
{/* onTransitionEnd={this.updateCodeWrapCollapseStates.bind(this)}*/}
987-
{/* >*/}
988-
{/* /!* <div*/}
989-
{/* class="js-code-wrap__header code-wrap__header"*/}
990-
{/* onDblClick={this.codeWrapHeaderDblClickHandler.bind(this)}*/}
991-
{/* >*/}
992-
{/* <label class="btn-group" dropdow title="Click to change">*/}
993-
{/* About*/}
994-
{/* </label>*/}
995-
{/* <div class="code-wrap__header-right-options">*/}
996-
{/* <a*/}
997-
{/* class="js-code-collapse-btn code-wrap__header-btn code-wrap__collapse-btn"*/}
998-
{/* title="Toggle code pane"*/}
999-
{/* onClick={this.collapseBtnHandler.bind(this)}*/}
1000-
{/* />*/}
1001-
{/* </div>*/}
1002-
{/* </div> *!/*/}
1003-
{/* <div className="cheat-sheet">*/}
1004-
{/* <table>*/}
1005-
{/* <tr>*/}
1006-
{/* <th>Feature</th>*/}
1007-
{/* <th>Sample</th>*/}
1008-
{/* </tr>*/}
1009-
{/* <tr>*/}
1010-
{/* <td>Participant</td>*/}
1011-
{/* <td>*/}
1012-
{/* ParticipantA*/}
1013-
{/* <br />*/}
1014-
{/* ParticipantB*/}
1015-
{/* </td>*/}
1016-
{/* </tr>*/}
1017-
{/* <tr>*/}
1018-
{/* <td>Message</td>*/}
1019-
{/* <td>A.messageA()</td>*/}
1020-
{/* </tr>*/}
1021-
{/* <tr>*/}
1022-
{/* <td>Asyc message</td>*/}
1023-
{/* <td>Alice-&gt;Bob: How are you?</td>*/}
1024-
{/* </tr>*/}
1025-
{/* <tr>*/}
1026-
{/* <td>Nested message</td>*/}
1027-
{/* <td>*/}
1028-
{/* A.messageA() {'{'}*/}
1029-
{/* <br />*/}
1030-
{/* &nbsp;&nbsp;B.messageB()*/}
1031-
{/* <br />*/}
1032-
{/* {'}'}*/}
1033-
{/* </td>*/}
1034-
{/* </tr>*/}
1035-
{/* <tr>*/}
1036-
{/* <td class="tg-0pky">Self-message</td>*/}
1037-
{/* <td class="tg-0pky">internalMessage()</td>*/}
1038-
{/* </tr>*/}
1039-
{/* <tr>*/}
1040-
{/* <td>Alt</td>*/}
1041-
{/* <td>*/}
1042-
{/* if (condition1) {'{'}*/}
1043-
{/* <br />*/}
1044-
{/* &nbsp;&nbsp;A.methodA()*/}
1045-
{/* <br />*/}
1046-
{/* {'}'} else if (condition2) {'{'}*/}
1047-
{/* <br />*/}
1048-
{/* &nbsp;&nbsp;B.methodB()*/}
1049-
{/* <br />*/}
1050-
{/* {'}'} else {'{'}*/}
1051-
{/* <br />*/}
1052-
{/* &nbsp;&nbsp;C.methodC()*/}
1053-
{/* <br />*/}
1054-
{/* {'}'}*/}
1055-
{/* </td>*/}
1056-
{/* </tr>*/}
1057-
{/* <tr>*/}
1058-
{/* <td>Loop</td>*/}
1059-
{/* <td>*/}
1060-
{/* while (condition) {'{'}*/}
1061-
{/* <br />*/}
1062-
{/* &nbsp;&nbsp;A.methodA()*/}
1063-
{/* <br />*/}
1064-
{/* {'}'}*/}
1065-
{/* </td>*/}
1066-
{/* </tr>*/}
1067-
{/* </table>*/}
1068-
{/* </div>*/}
1069-
{/* </div>*/}
1070-
{/*</div>*/}
1071987
</Tabs>
1072988
</div>
1073-
{/*<SplitPane*/}
1074-
{/*class="code-side"*/}
1075-
{/*id="js-code-side"*/}
1076-
{/*sizes={this.state.codeSplitSizes}*/}
1077-
{/*minSize={minCodeWrapSize}*/}
1078-
{/*direction={*/}
1079-
{/*this.props.currentLayoutMode === 2 ||*/}
1080-
{/*this.props.currentLayoutMode === 5*/}
1081-
{/*? 'horizontal'*/}
1082-
{/*: 'vertical'*/}
1083-
{/*}*/}
1084-
{/*onDragStart={this.codeSplitDragStart.bind(this)}*/}
1085-
{/*onDragEnd={this.codeSplitDragEnd.bind(this)}*/}
1086-
{/*onSplit={splitInstance => (this.codeSplitInstance = splitInstance)}*/}
1087-
{/*>*/}
1088-
{/**/}
1089-
{/**/}
1090-
{/*</Tabs>*/}
1091989
<div class="demo-side" id="js-demo-side">
1092990
<div className="h-full flex flex-col">
1093991
<div
@@ -1137,42 +1035,53 @@ export default class ContentWrap extends Component {
11371035
</div>
11381036
<div className="flex items-center gap-3 text-sm font-semibold">
11391037
<button
1140-
className="px-3 py-1 bg-gray-300 text-gray-600 flex items-center gap-1.5 rounded-lg hover:bg-gray-400 duration-200"
1141-
aria-label="Export as PNG"
1142-
onClick={this.exportPngClickHandler.bind(this)}
1038+
className="px-3 py-1 bg-gray-300 text-gray-600 flex items-center gap-1.5 rounded-lg hover:bg-gray-400 duration-200"
1039+
aria-label="Toggle Fullscreen"
1040+
onClick={this.toggleFullscreen.bind(this)}
1041+
title="Toggle Fullscreen Presenting Mode"
1042+
>
1043+
<svg className="w-5 h-5 fill-current">
1044+
<use xlinkHref="#fullscreen-icon"/>
1045+
</svg>
1046+
<span>Present</span>
1047+
</button>
1048+
<button
1049+
className="px-3 py-1 bg-gray-300 text-gray-600 flex items-center gap-1.5 rounded-lg hover:bg-gray-400 duration-200"
1050+
aria-label="Export as PNG"
1051+
onClick={this.exportPngClickHandler.bind(this)}
11431052
>
11441053
<svg className="w-5 h-5 fill-current">
1145-
<use xlinkHref="#icon-download" />
1054+
<use xlinkHref="#icon-download"/>
11461055
</svg>
11471056
<span>PNG</span>
11481057
</button>
11491058
<button
1150-
className="px-3 py-1 bg-gray-300 text-gray-600 flex items-center gap-1.5 rounded-lg hover:bg-gray-400 duration-200"
1151-
aria-label="Copy PNG to Clipboard"
1152-
onClick={this.copyImageClickHandler.bind(this)}
1059+
className="px-3 py-1 bg-gray-300 text-gray-600 flex items-center gap-1.5 rounded-lg hover:bg-gray-400 duration-200"
1060+
aria-label="Copy PNG to Clipboard"
1061+
onClick={this.copyImageClickHandler.bind(this)}
11531062
>
11541063
<svg className="w-5 h-5 fill-current">
1155-
<use xlinkHref="#icon-copy" />
1064+
<use xlinkHref="#icon-copy"/>
11561065
</svg>
11571066
<span>Copy PNG</span>
11581067
</button>
11591068
</div>
11601069
</div>
11611070
)}
11621071
<Console
1163-
isConsoleOpen={this.state.isConsoleOpen}
1164-
onConsoleHeaderDblClick={this.consoleHeaderDblClickHandler.bind(
1165-
this,
1166-
)}
1167-
onClearConsoleBtnClick={this.clearConsoleBtnClickHandler.bind(
1168-
this,
1169-
)}
1170-
toggleConsole={this.toggleConsole.bind(this)}
1171-
onEvalInputKeyup={this.evalConsoleExpr.bind(this)}
1172-
onReady={(el) => (this.consoleCm = el)}
1072+
isConsoleOpen={this.state.isConsoleOpen}
1073+
onConsoleHeaderDblClick={this.consoleHeaderDblClickHandler.bind(
1074+
this,
1075+
)}
1076+
onClearConsoleBtnClick={this.clearConsoleBtnClickHandler.bind(
1077+
this,
1078+
)}
1079+
toggleConsole={this.toggleConsole.bind(this)}
1080+
onEvalInputKeyup={this.evalConsoleExpr.bind(this)}
1081+
onReady={(el) => (this.consoleCm = el)}
11731082
/>
11741083
<CssSettingsModal
1175-
show={this.state.isCssSettingsModalOpen}
1084+
show={this.state.isCssSettingsModalOpen}
11761085
closeHandler={async () =>
11771086
await this.setState({ isCssSettingsModalOpen: false })
11781087
}

src/components/Icons.jsx

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -132,6 +132,9 @@ export function Icons() {
132132
<symbol id="keyboard-icon" viewBox="0 0 24 24">
133133
<path d="M19,10H17V8H19M19,13H17V11H19M16,10H14V8H16M16,13H14V11H16M16,17H8V15H16M7,10H5V8H7M7,13H5V11H7M8,11H10V13H8M8,8H10V10H8M11,11H13V13H11M11,8H13V10H11M20,5H4C2.89,5 2,5.89 2,7V17A2,2 0 0,0 4,19H20A2,2 0 0,0 22,17V7C22,5.89 21.1,5 20,5Z" />
134134
</symbol>
135+
<symbol id="fullscreen-icon" viewBox="0 0 24 24">
136+
<path d="M7 14H5v5h5v-2H7v-3zm-2-4h2V7h3V5H5v5zm12 7h-3v2h5v-5h-2v3zM14 5v2h3v3h2V5h-5z"/>
137+
</symbol>
135138
<symbol id="mode-icon" viewBox="0 0 100 100">
136139
<g>
137140
<rect x={0} y={0} width={28} height={47} />

0 commit comments

Comments
 (0)