1
+ /* -*- mode: java; c-basic-offset: 2; indent-tabs-mode: nil -*- */ /*
2
+ Part of the Processing project - http://processing.org
3
+
4
+ Copyright (c) 2015 The Processing Foundation
5
+
6
+ This program is free software; you can redistribute it and/or
7
+ modify it under the terms of the GNU General Public License
8
+ version 2, as published by the Free Software Foundation.
9
+
10
+ This program is distributed in the hope that it will be useful,
11
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13
+ GNU General Public License for more details.
14
+
15
+ You should have received a copy of the GNU General Public License
16
+ along with this program; if not, write to the Free Software Foundation,
17
+ Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18
+ */
19
+ package processing .app
20
+
21
+ import processing .app .ui .Toolkit
22
+ import java .awt .EventQueue
23
+ import java .awt .Frame
24
+ import java .io .PrintWriter
25
+ import java .io .StringWriter
26
+ import javax .swing .JFrame
27
+ import javax .swing .JOptionPane
28
+
29
+ class Messages {
30
+ companion object {
31
+ /**
32
+ * "No cookie for you" type messages. Nothing fatal or all that
33
+ * much of a bummer, but something to notify the user about.
34
+ */
35
+ @ JvmStatic
36
+ fun showMessage (title : String = "Message" , message : String ) {
37
+ if (Base .isCommandLine ()) {
38
+ println ("$title: $message" )
39
+ } else {
40
+ JOptionPane .showMessageDialog (
41
+ Frame (), message , title ,
42
+ JOptionPane .INFORMATION_MESSAGE
43
+ )
44
+ }
45
+ }
46
+
47
+
48
+ /**
49
+ * Non-fatal error message with optional stack trace side dish.
50
+ */
51
+ /**
52
+ * Non-fatal error message.
53
+ */
54
+ @ JvmStatic
55
+ @ JvmOverloads
56
+ fun showWarning (title : String = "Warning" , message : String , e : Throwable ? = null ) {
57
+ if (Base .isCommandLine ()) {
58
+ println ("$title: $message" )
59
+ } else {
60
+ JOptionPane .showMessageDialog (
61
+ Frame (), message , title ,
62
+ JOptionPane .WARNING_MESSAGE
63
+ )
64
+ }
65
+ e ?.printStackTrace ()
66
+ }
67
+
68
+ /**
69
+ * Non-fatal error message with two levels of formatting.
70
+ * Unlike the others, this is non-blocking and will run later on the EDT.
71
+ */
72
+ @ JvmStatic
73
+ fun showWarningTiered (
74
+ title : String ,
75
+ primary : String , secondary : String ,
76
+ e : Throwable ?
77
+ ) {
78
+ if (Base .isCommandLine ()) {
79
+ // TODO All these messages need to be handled differently for
80
+ // proper parsing on the command line. Many have \n in them.
81
+ println ("$title: $primary\n $secondary" )
82
+ } else {
83
+ EventQueue .invokeLater {
84
+ JOptionPane .showMessageDialog (
85
+ JFrame (),
86
+ Toolkit .formatMessage (primary , secondary ),
87
+ title , JOptionPane .WARNING_MESSAGE
88
+ )
89
+ }
90
+ }
91
+ e ?.printStackTrace ()
92
+ }
93
+
94
+
95
+ /**
96
+ * Show an error message that's actually fatal to the program.
97
+ * This is an error that can't be recovered. Use showWarning()
98
+ * for errors that allow P5 to continue running.
99
+ */
100
+ @ JvmStatic
101
+ fun showError (title : String = "Error" , message : String , e : Throwable ?) {
102
+ if (Base .isCommandLine ()) {
103
+ System .err .println ("$title: $message" )
104
+ } else {
105
+ JOptionPane .showMessageDialog (
106
+ Frame (), message , title ,
107
+ JOptionPane .ERROR_MESSAGE
108
+ )
109
+ }
110
+ e ?.printStackTrace ()
111
+ System .exit (1 )
112
+ }
113
+
114
+
115
+ /**
116
+ * Warning window that includes the stack trace.
117
+ */
118
+ @ JvmStatic
119
+ fun showTrace (
120
+ title : String ?,
121
+ message : String ,
122
+ t : Throwable ?,
123
+ fatal : Boolean
124
+ ) {
125
+ val title = title ? : if (fatal ) "Error" else "Warning"
126
+
127
+ if (Base .isCommandLine ()) {
128
+ System .err .println ("$title: $message" )
129
+ t ?.printStackTrace ()
130
+ } else {
131
+ val sw = StringWriter ()
132
+ t !!.printStackTrace (PrintWriter (sw ))
133
+
134
+ JOptionPane .showMessageDialog (
135
+ Frame (), // first <br/> clears to the next line
136
+ // second <br/> is a shorter height blank space before the trace
137
+ Toolkit .formatMessage ("$message<br/><tt><br/>$sw</tt>" ),
138
+ title ,
139
+ if (fatal ) JOptionPane .ERROR_MESSAGE else JOptionPane .WARNING_MESSAGE
140
+ )
141
+
142
+ if (fatal ) {
143
+ System .exit (1 )
144
+ }
145
+ }
146
+ }
147
+
148
+ @ JvmStatic
149
+ fun showYesNoQuestion (
150
+ editor : Frame ?, title : String ?,
151
+ primary : String ?, secondary : String ?
152
+ ): Int {
153
+ if (!Platform .isMacOS ()) {
154
+ return JOptionPane .showConfirmDialog (
155
+ editor ,
156
+ Toolkit .formatMessage (primary , secondary ), //"<html><body>" +
157
+ //"<b>" + primary + "</b>" +
158
+ //"<br>" + secondary,
159
+ title ,
160
+ JOptionPane .YES_NO_OPTION ,
161
+ JOptionPane .QUESTION_MESSAGE
162
+ )
163
+ } else {
164
+ val result = showCustomQuestion (
165
+ editor , title , primary , secondary ,
166
+ 0 , "Yes" , "No"
167
+ )
168
+ return if (result == 0 ) {
169
+ JOptionPane .YES_OPTION
170
+ } else if (result == 1 ) {
171
+ JOptionPane .NO_OPTION
172
+ } else {
173
+ JOptionPane .CLOSED_OPTION
174
+ }
175
+ }
176
+ }
177
+
178
+
179
+ /**
180
+ * @param highlight A valid array index for options[] that specifies the
181
+ * default (i.e. safe) choice.
182
+ * @return The (zero-based) index of the selected value, -1 otherwise.
183
+ */
184
+ @ JvmStatic
185
+ fun showCustomQuestion (
186
+ editor : Frame ?, title : String ?,
187
+ primary : String ?, secondary : String ?,
188
+ highlight : Int , vararg options : String
189
+ ): Int {
190
+ val result : Any
191
+ if (!Platform .isMacOS ()) {
192
+ return JOptionPane .showOptionDialog (
193
+ editor ,
194
+ Toolkit .formatMessage (primary , secondary ), title ,
195
+ JOptionPane .DEFAULT_OPTION , JOptionPane .QUESTION_MESSAGE , null ,
196
+ options , options [highlight ]
197
+ )
198
+ } else {
199
+ val pane =
200
+ JOptionPane (
201
+ Toolkit .formatMessage (primary , secondary ),
202
+ JOptionPane .QUESTION_MESSAGE
203
+ )
204
+
205
+ pane .options = options
206
+
207
+ // highlight the safest option ala apple hig
208
+ pane .initialValue = options [highlight ]
209
+
210
+ val dialog = pane .createDialog (editor , null )
211
+ dialog .isVisible = true
212
+
213
+ result = pane .value
214
+ }
215
+ for (i in options .indices ) {
216
+ if (result != null && result == options [i ]) return i
217
+ }
218
+ return -1
219
+ }
220
+
221
+
222
+ // . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
223
+ @ JvmStatic
224
+ @ Deprecated ("Use log() instead" )
225
+ fun log (from : Any , message : String ) {
226
+ if (Base .DEBUG ) {
227
+ val callingClass = Throwable ()
228
+ .stackTrace [2 ]
229
+ .className
230
+ .formatClassName ()
231
+ println ("$callingClass: $message" )
232
+ }
233
+ }
234
+
235
+ @ JvmStatic
236
+ fun log (message : String ?) {
237
+ if (Base .DEBUG ) {
238
+ val callingClass = Throwable ()
239
+ .stackTrace [2 ]
240
+ .className
241
+ .formatClassName ()
242
+ println ("$callingClass$message" )
243
+ }
244
+ }
245
+
246
+ @ JvmStatic
247
+ fun logf (message : String ?, vararg args : Any ?) {
248
+ if (Base .DEBUG ) {
249
+ val callingClass = Throwable ()
250
+ .stackTrace [2 ]
251
+ .className
252
+ .formatClassName ()
253
+ System .out .printf ("$callingClass$message" , *args )
254
+ }
255
+ }
256
+
257
+ @ JvmStatic
258
+ @ JvmOverloads
259
+ fun err (message : String ?, e : Throwable ? = null ) {
260
+ if (Base .DEBUG ) {
261
+ if (message != null ) {
262
+ val callingClass = Throwable ()
263
+ .stackTrace [4 ]
264
+ .className
265
+ .formatClassName ()
266
+ System .err .println ("$callingClass$message" )
267
+ }
268
+ e ?.printStackTrace ()
269
+ }
270
+ }
271
+ }
272
+ }
273
+
274
+ // Helper functions to give the base classes a color
275
+ fun String .formatClassName () = this
276
+ .replace ("processing." , "" )
277
+ .replace ("." , "/" )
278
+ .padEnd (40 )
279
+ .colorizePathParts ()
280
+ fun String .colorizePathParts () = split ("/" ).joinToString ("/" ) { part ->
281
+ "\u001B [${31 + (part.hashCode() and 0x7).rem(6)}m$part\u001B [0m"
282
+ }
0 commit comments