100% found this document useful (1 vote)
16 views82 pages

Programming Cocoa With Ruby Create Compelling Mac Apps Using Rubycocoa The Facets of Ruby Series 1st Edition Brian Marick Instant Download

Programming Cocoa with Ruby by Brian Marick is a comprehensive guide for developers looking to create Mac applications using RubyCocoa. The book provides insights into Cocoa technology and practical examples to ease the learning curve for those familiar with Ruby or Python. It includes detailed explanations of core concepts and development practices essential for building compelling Mac apps.

Uploaded by

teburchabih
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
100% found this document useful (1 vote)
16 views82 pages

Programming Cocoa With Ruby Create Compelling Mac Apps Using Rubycocoa The Facets of Ruby Series 1st Edition Brian Marick Instant Download

Programming Cocoa with Ruby by Brian Marick is a comprehensive guide for developers looking to create Mac applications using RubyCocoa. The book provides insights into Cocoa technology and practical examples to ease the learning curve for those familiar with Ruby or Python. It includes detailed explanations of core concepts and development practices essential for building compelling Mac apps.

Uploaded by

teburchabih
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 82

Programming Cocoa With Ruby Create Compelling

Mac Apps Using Rubycocoa The Facets Of Ruby


Series 1st Edition Brian Marick download

https://ebookbell.com/product/programming-cocoa-with-ruby-create-
compelling-mac-apps-using-rubycocoa-the-facets-of-ruby-
series-1st-edition-brian-marick-2091668

Explore and download more ebooks at ebookbell.com


Here are some recommended products that we believe you will be
interested in. You can click the link to download.

Mastering Macos Programming Combine Macos Programming With Cocoa And


Swift 3 To Build Powerful Applications Grimshaw

https://ebookbell.com/product/mastering-macos-programming-combine-
macos-programming-with-cocoa-and-swift-3-to-build-powerful-
applications-grimshaw-11409396

Ios 12 Programming Fundamentals With Swift Swift Xcode And Cocoa


Basics 5th Edition Matt Neuburg

https://ebookbell.com/product/ios-12-programming-fundamentals-with-
swift-swift-xcode-and-cocoa-basics-5th-edition-matt-neuburg-22034678

Ios 15 Programming Fundamentals With Swift Swift Xcode And Cocoa


Basics 8th Edition Matt Neuburg

https://ebookbell.com/product/ios-15-programming-fundamentals-with-
swift-swift-xcode-and-cocoa-basics-8th-edition-matt-neuburg-36104646

Ios 9 Programming Fundamentals With Swift Swift Xcode And Cocoa Basics
2nd Edition Matt Neuburg

https://ebookbell.com/product/ios-9-programming-fundamentals-with-
swift-swift-xcode-and-cocoa-basics-2nd-edition-matt-neuburg-5313850
Ios 8 Programming Fundamentals With Swift Swift Xcode And Cocoa Basics
1st Edition Matt Neuburg

https://ebookbell.com/product/ios-8-programming-fundamentals-with-
swift-swift-xcode-and-cocoa-basics-1st-edition-matt-neuburg-5471624

Ios 10 Programming Fundamentals With Swift Swift Xcode And Cocoa


Basics 3rd Edition Matt Neuburg

https://ebookbell.com/product/ios-10-programming-fundamentals-with-
swift-swift-xcode-and-cocoa-basics-3rd-edition-matt-neuburg-5563990

Ios 11 Programming Fundamentals With Swift Swift Xcode And Cocoa


Basics 4th Edition Matt Neuburg

https://ebookbell.com/product/ios-11-programming-fundamentals-with-
swift-swift-xcode-and-cocoa-basics-4th-edition-matt-neuburg-10365296

Ios 13 Programming Fundamentals With Swift Swift Xcode And Cocoa


Basics Sixth Edition Matt Neuburg

https://ebookbell.com/product/ios-13-programming-fundamentals-with-
swift-swift-xcode-and-cocoa-basics-sixth-edition-matt-neuburg-11903566

Ios 14 Programming Fundamentals With Swift Swift Xcode And Cocoa


Basics 7th Edition Matt Neuburg

https://ebookbell.com/product/ios-14-programming-fundamentals-with-
swift-swift-xcode-and-cocoa-basics-7th-edition-matt-neuburg-11950384
What Readers Are Saying About
Programming Cocoa with Ruby

This isn’t just a book on RubyCocoa; it is probably the best book I’ve
seen that explains Cocoa technology. It actually explains how some of
the core technologies, especially bindings, work instead of just show-
ing an example of how to use them.
Allison Newman
Cocoa application developer

Learning a new API is hard enough, but learning a new API and a new
programming language at the same time can be overwhelming. Pro-
gramming Cocoa with Ruby is written for those of us used to a lan-
guage like Ruby or Python who want to learn about all the great stuff
Cocoa has to offer.
Jeremy McAnally
Developer, entp

The influence of Smalltalk on Ruby and Objective-C is considerable.


It shouldn’t be a surprise then that Cocoa, whose native tongue is
Objective-C, can be effectively learned and programmed from Ruby
in a way that captures the succinctness and expressiveness of this
newly popular scripting language. Brian’s book is a great introduc-
tion to the agile development of Cocoa apps, it serves as a primer on
Cocoa, and it demonstrates sound and thoughtful development prac-
tices and hygiene throughout.
Jerry Kuch
Principal engineer, EMC Corporation
Programming Cocoa with Ruby
Create Compelling Mac Apps Using RubyCocoa

Brian Marick

The Pragmatic Bookshelf


Raleigh, North Carolina Dallas, Texas
Many of the designations used by manufacturers and sellers to distinguish their prod-
ucts are claimed as trademarks. Where those designations appear in this book, and The
Pragmatic Programmers, LLC was aware of a trademark claim, the designations have
been printed in initial capital letters or in all capitals. The Pragmatic Starter Kit, The
Pragmatic Programmer, Pragmatic Programming, Pragmatic Bookshelf and the linking g
device are trademarks of The Pragmatic Programmers, LLC.

Every precaution was taken in the preparation of this book. However, the publisher
assumes no responsibility for errors or omissions, or for damages that may result from
the use of information (including program listings) contained herein.

Our Pragmatic courses, workshops, and other products can help you and your team
create better software and have more fun. For more information, as well as the latest
Pragmatic titles, please visit us at

http://www.pragprog.com

Copyright © 2009 Brian Marick.

All rights reserved.

No part of this publication may be reproduced, stored in a retrieval system, or transmit-


ted, in any form, or by any means, electronic, mechanical, photocopying, recording, or
otherwise, without the prior consent of the publisher.

Printed in the United States of America.

ISBN-10: 1-934356-19-0
ISBN-13: 978-1-934356-19-7
Printed on acid-free paper.
P1.0 printing, July 2009
Version: 2009-8-6
Contents
1 Introduction 11
1.1 What Is Cocoa? . . . . . . . . . . . . . . . . . . . . . . . 12
1.2 What Is RubyCocoa? . . . . . . . . . . . . . . . . . . . . 12
1.3 What’s It Like to Learn Cocoa Using Ruby? . . . . . . . 12
1.4 RubyCocoa? That’s So Last Year! . . . . . . . . . . . . . 13
1.5 Prerequisites . . . . . . . . . . . . . . . . . . . . . . . . . 13
1.6 Versions . . . . . . . . . . . . . . . . . . . . . . . . . . . 15
1.7 Our Example App . . . . . . . . . . . . . . . . . . . . . . 16
1.8 Centuries of the Bookmaker’s Art: Scorned . . . . . . . 18
1.9 Some Terminology . . . . . . . . . . . . . . . . . . . . . 19
1.10 Service After the Sale . . . . . . . . . . . . . . . . . . . . 19
1.11 Solving Problems . . . . . . . . . . . . . . . . . . . . . . 19
1.12 Acknowledgments . . . . . . . . . . . . . . . . . . . . . . 20

2 How Do We Get This Thing Started? 22


2.1 A Program That Prints . . . . . . . . . . . . . . . . . . . 23
2.2 Putting an Item in the Status Bar . . . . . . . . . . . . 26
2.3 Menus . . . . . . . . . . . . . . . . . . . . . . . . . . . . 27
2.4 An Application Bundle . . . . . . . . . . . . . . . . . . . 31
2.5 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 35

I A First Realistic App 36

3 Working with Interface Builder and Xcode 37


3.1 The Basics . . . . . . . . . . . . . . . . . . . . . . . . . . 38
3.2 Creating and Editing Classes in Xcode . . . . . . . . . . 48
3.3 Debugging . . . . . . . . . . . . . . . . . . . . . . . . . . 55
3.4 Synchronizing Interface Builder and Xcode . . . . . . . 57
3.5 Attributes . . . . . . . . . . . . . . . . . . . . . . . . . . 58
3.6 Overriding Window Behavior with a Delegate . . . . . . 60
CONTENTS 6

3.7 Try This Yourself . . . . . . . . . . . . . . . . . . . . . . 61


3.8 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 61

4 One Good App Observes Another 62


4.1 Notifications Within an App . . . . . . . . . . . . . . . . 62
4.2 Notifications Between Apps . . . . . . . . . . . . . . . . 67
4.3 The App to Fenestrate . . . . . . . . . . . . . . . . . . . 70
4.4 Putting Notification Handling Behind the GUI . . . . . 71
4.5 Reopening Objective-C Classes . . . . . . . . . . . . . . 73
4.6 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 73

II Reshaping Fenestra 75

5 A Better GUI 76
5.1 Toggle Buttons . . . . . . . . . . . . . . . . . . . . . . . 77
5.2 The Default Button . . . . . . . . . . . . . . . . . . . . . 78
5.3 Combo Box Items . . . . . . . . . . . . . . . . . . . . . . 79
5.4 The Initial First Responder . . . . . . . . . . . . . . . . 80
5.5 Try This Yourself . . . . . . . . . . . . . . . . . . . . . . 80
5.6 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 81

6 Decoupled Controllers 82
6.1 Ignorant Objects . . . . . . . . . . . . . . . . . . . . . . 83
6.2 Extracting Subclasses . . . . . . . . . . . . . . . . . . . 85
6.3 Reacting to Button State . . . . . . . . . . . . . . . . . . 90
6.4 Using Nibs to Avoid Dependencies . . . . . . . . . . . . 90
6.5 Initializing Combo Boxes . . . . . . . . . . . . . . . . . . 92
6.6 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 93

7 Notifications Connect Decoupled Objects 94


7.1 Controllers . . . . . . . . . . . . . . . . . . . . . . . . . . 94
7.2 Translators and the Rising Tide of Ugliness . . . . . . . 96
7.3 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 99

8 More Expressive Code 100


8.1 A DSL for Notifications . . . . . . . . . . . . . . . . . . . 101
8.2 RubyCocoa Has Two Ways of Referring to Superclasses 103
8.3 Shorthand for Posting Notifications . . . . . . . . . . . 103
8.4 Try This Yourself . . . . . . . . . . . . . . . . . . . . . . 105
8.5 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 107

Report erratum
this copy is (P1.0 printing, July 2009)
CONTENTS 7

III Project Mechanics 108

9 Bundling Gems and Libraries with Your App 109


9.1 Manual Control . . . . . . . . . . . . . . . . . . . . . . . 110
9.2 Standaloneify . . . . . . . . . . . . . . . . . . . . . . . . 114
9.3 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 116

10 Project Organization, Builds, and Your Favorite Editor 117


10.1 Groups . . . . . . . . . . . . . . . . . . . . . . . . . . . . 118
10.2 Using Xcode with Hierarchical Project Folders . . . . . 119
10.3 Running in Place . . . . . . . . . . . . . . . . . . . . . . 121
10.4 Building Without Xcode . . . . . . . . . . . . . . . . . . 121
10.5 Using Interface Builder with Hierarchical Project Folders 123
10.6 Starting a New Project . . . . . . . . . . . . . . . . . . . 124
10.7 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 125

IV Declarative Data Handling 126

11 Persistent User Preferences 127


11.1 The User Preferences System . . . . . . . . . . . . . . . 128
11.2 Storing Custom Objects as Preferences . . . . . . . . . 131
11.3 Using Archived Objects . . . . . . . . . . . . . . . . . . . 139
11.4 Views Can Pull Data . . . . . . . . . . . . . . . . . . . . 143
11.5 Try This Yourself: A Sticky Window . . . . . . . . . . . 145
11.6 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 149

12 Creating a Preference Panel in a New Nib 150


12.1 Creating a Nib . . . . . . . . . . . . . . . . . . . . . . . . 151
12.2 Drawing the Panel . . . . . . . . . . . . . . . . . . . . . 153
12.3 Hooking the Panel to the App . . . . . . . . . . . . . . . 155
12.4 The Nib File’s Owner . . . . . . . . . . . . . . . . . . . . 158
12.5 IB’s First Responder Pseudo-Object . . . . . . . . . . . 159
12.6 Memory Leaks . . . . . . . . . . . . . . . . . . . . . . . . 160
12.7 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 161

13 Implementing a Preference Panel with Cocoa Bindings 162


13.1 Binding a Simple Value . . . . . . . . . . . . . . . . . . 162
13.2 Binding an Array of Hashes . . . . . . . . . . . . . . . . 166
13.3 Formatters . . . . . . . . . . . . . . . . . . . . . . . . . . 172
13.4 Value Transformers . . . . . . . . . . . . . . . . . . . . . 177

Report erratum
this copy is (P1.0 printing, July 2009)
CONTENTS 8

13.5 Adding and Deleting Table Rows . . . . . . . . . . . . . 182


13.6 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 184

14 Setting Up Bindings with Code 185


14.1 Oh No! Terminology! . . . . . . . . . . . . . . . . . . . . 185
14.2 Using Rooted Keypaths in Code . . . . . . . . . . . . . . 189
14.3 Subclassing NSArrayController . . . . . . . . . . . . . . 189
14.4 bind_toObject_withKeyPath_options . . . . . . . . . . . 192
14.5 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 196

V Fun with Tables 197

15 Prologue: Folders and Tests 198


15.1 Disk Layout . . . . . . . . . . . . . . . . . . . . . . . . . 198

16 Selections and Editing 202


16.1 An Example of Creating Tests: The Add Method . . . . 202
16.2 Working with an Uncooperative Control . . . . . . . . . 212
16.3 Try This Yourself . . . . . . . . . . . . . . . . . . . . . . 220
16.4 Building Setup Methods . . . . . . . . . . . . . . . . . . 227
16.5 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 229

17 Buttons in Tables 230


17.1 Cells . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 230
17.2 Making the Change . . . . . . . . . . . . . . . . . . . . . 231
17.3 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 233

18 A Formatter with Two Wrinkles 234


18.1 The Formatter Code . . . . . . . . . . . . . . . . . . . . 235
18.2 Calling Methods That Take Reference Arguments . . . 237
18.3 Breaking Encapsulation in Tests . . . . . . . . . . . . . 240
18.4 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 242

19 Picking Files with Open Panels 243


19.1 NSOpenPanel . . . . . . . . . . . . . . . . . . . . . . . . 243
19.2 A Design for Using NSOpenPanel in Fenestra . . . . . . 246
19.3 Try This Yourself: PreferencesController Tests . . . . . 248
19.4 Try This Yourself: The NSOpenPanel Controller . . . . 256
19.5 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 258

Report erratum
this copy is (P1.0 printing, July 2009)
CONTENTS 9

20 Drag and Drop 261


20.1 How Drag and Drop Works . . . . . . . . . . . . . . . . 261
20.2 Designing the GUI . . . . . . . . . . . . . . . . . . . . . 263
20.3 A Template for the Solution . . . . . . . . . . . . . . . . 264
20.4 Utility Classes and Modules . . . . . . . . . . . . . . . . 265
20.5 Try This Yourself: Lively Dragging Info . . . . . . . . . . 268
20.6 Try This Yourself: Drag and Drop . . . . . . . . . . . . . 275
20.7 Does It Work? . . . . . . . . . . . . . . . . . . . . . . . . 280
20.8 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 281

21 Epilogue: A Wonderful World of Tests 282


21.1 Test-Driven Design . . . . . . . . . . . . . . . . . . . . . 282
21.2 To Learn More . . . . . . . . . . . . . . . . . . . . . . . . 285

VI Wrapping Up 286

22 Fit and Finish 287


22.1 Saving the Window Position Until the Next Launch . . 287
22.2 Tab Behavior . . . . . . . . . . . . . . . . . . . . . . . . . 288
22.3 Using NSMatrix to Organize Buttons . . . . . . . . . . . 289
22.4 Sizing . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 293
22.5 Cleaning Up the Menu Bar . . . . . . . . . . . . . . . . 297
22.6 The About Window . . . . . . . . . . . . . . . . . . . . . 297
22.7 Changing the Application’s Name . . . . . . . . . . . . . 299

23 Adding Help 301


23.1 Help Book Basics . . . . . . . . . . . . . . . . . . . . . . 301
23.2 Creating a Help Book . . . . . . . . . . . . . . . . . . . . 302
23.3 Editing Pages . . . . . . . . . . . . . . . . . . . . . . . . 303
23.4 Hooking a Help Book into an App . . . . . . . . . . . . . 309
23.5 A Workflow for Creating Help Book Pages . . . . . . . . 311
23.6 Tooltips . . . . . . . . . . . . . . . . . . . . . . . . . . . . 311

24 Document-Based Applications 313


24.1 The Major Players . . . . . . . . . . . . . . . . . . . . . . 314
24.2 The Responder Chain . . . . . . . . . . . . . . . . . . . . 316
24.3 Creating a New Document . . . . . . . . . . . . . . . . . 319
24.4 Opening and Saving Documents . . . . . . . . . . . . . 328
24.5 Editing . . . . . . . . . . . . . . . . . . . . . . . . . . . . 330
24.6 Learning More . . . . . . . . . . . . . . . . . . . . . . . . 333

Report erratum
this copy is (P1.0 printing, July 2009)
CONTENTS 10

25 MacRuby 334
25.1 Getting MacRuby . . . . . . . . . . . . . . . . . . . . . . 337
25.2 MacRuby Basics . . . . . . . . . . . . . . . . . . . . . . . 337
25.3 A MacRuby Checklist . . . . . . . . . . . . . . . . . . . . 339
25.4 What Now? . . . . . . . . . . . . . . . . . . . . . . . . . . 343

VII Reference 344

26 The Objective-C Bridge and Bridge Metadata 345


26.1 An Unexpected Return Value . . . . . . . . . . . . . . . 345
26.2 What Information Can Be Found at Runtime? . . . . . 346
26.3 Supplementing Runtime Information . . . . . . . . . . 347
26.4 Our Own Private Metadata . . . . . . . . . . . . . . . . . 348
26.5 Finding Out More . . . . . . . . . . . . . . . . . . . . . . 349

27 The Underpinnings of Cocoa Bindings 350


27.1 Requirements . . . . . . . . . . . . . . . . . . . . . . . . 350
27.2 Our Goal . . . . . . . . . . . . . . . . . . . . . . . . . . . 351
27.3 Declaring Observed Properties . . . . . . . . . . . . . . 352
27.4 Observing Changes . . . . . . . . . . . . . . . . . . . . . 353
27.5 Implementing bind_toObject_withKeyPath_options . . 355
27.6 Changing the Value of an Observed Key . . . . . . . . . 356
27.7 In Summary... . . . . . . . . . . . . . . . . . . . . . . . . 357
27.8 Postscript: Observing Changes to Collections . . . . . . 359

A Glossary 361

B Bibliography 372

Index 376

Report erratum
this copy is (P1.0 printing, July 2009)
Chapter 1

Introduction
It’s simple, really: if you like Ruby and you like Macs and you want
to put the two together, this book is for you. After you read through
it. . . wait, scratch that—after you work through it, you’ll be able to build
nice, Mac-like apps. You’ll have the memory of doing, at least once,
many of the tasks that make up building a Mac app. Your life will have
much less of the “What do I do now?” frustration that sinks so many
first attempts to use a big and complicated framework.
I endured that frustration for you. When I started writing the book, I
knew practically nothing about coding Mac GUI apps (in Ruby or any
other language). I learned how in my usual way: by diving into coding
something too ambitious. As always happens, I spent much of my time
blundering down blind alleys, staring at app crashes and weird behav-
iors, figuring out what pieces of the conceptual puzzle I was missing,
searching for them in vast masses of documentation, and revisiting old
code in the light of new understanding. The only difference was that
after I figured something out, I wrote a new chapter about what I’d
done and what I’d learned—except that I removed most of the frustra-
tion from the story line. When I had to backtrack because I didn’t know
something, I wrote that something into the story just when I would have
needed it. The result is what Imre Lakatos, the philosopher of science,
called a rational reconstruction of history: follow the book, and I think
you’ll get pretty much the experience I should have had.
That turns out to be a fantastically time-consuming way of writing a
book. The payoff is that, when I wrote, the experience of learning was
fresh in my mind. Experts often have a problem remembering what it
was like to learn and how much they used to not know. I solved that
problem by being barely not ignorant as I wrote.
W HAT I S C OCOA ? 12

1.1 What Is Cocoa?


Most modern Mac applications are written using the Cocoa framework.
Cocoa is an object-oriented framework that structures your app and
handles a lot of drudgery for you. It mostly makes developing a user
interface easier, but it also has classes and libraries for handling the
file system, interprocess communication, persistent data, and so on.

1.2 What Is RubyCocoa?


The Cocoa framework was originally designed to be used via Objective-
C programs. Objective-C is an object-oriented dialect of C. Early in the
history of OS X, Apple also provided Java interfaces to some of the
framework, but that didn’t work out well. The problem was that Java
wants to know things at compile time that Objective-C defers to run-
time. For example, Objective-C is not nearly so picky about declaring
types as Java is. Because Cocoa framework writers took advantage of
such features, the mapping between Java and Cocoa was clumsy.
It’s much easier to build a bridge between Cocoa and Ruby because
Ruby and Objective-C stem from similar philosophies of language de-
sign. RubyCocoa is that bridge. With it, you can write Ruby code that
calls Objective-C code, and vice versa. So, it’s quite possible to write a
Mac app in Ruby.

1.3 What’s It Like to Learn Cocoa Using Ruby?


It doesn’t take much time to learn the basics of RubyCocoa. Once you’ve
done that, you’ll spend most of your time learning Cocoa. Your Cocoa
learning will occasionally be interrupted by some surprising RubyCocoa
fact, which you will then absorb and move on.
This book follows that sequence. It begins with an introductory chapter
that teaches RubyCocoa basics without many of the distractions of a
real user interface. Then it follows a typical development pattern: begin
with a small version of your app, get it working, find the next thing you
wish it did, make it do that, and repeat until you’re done. Cocoa and
RubyCocoa topics will be covered as they come up in a realistic course
of development.
With any complex framework, there’s a moment when you realize you
finally have a feel for it—when faced with a new problem, you’re able to

Report erratum
this copy is (P1.0 printing, July 2009)
R UBY C OCOA ? T HAT ’ S So L AST Y EAR ! 13

guess whether the framework addresses it, roughly how it will address
it, and where to look to find the details. The aim of this book is to give
you that feel for Cocoa and RubyCocoa. It’s not a reference to the Cocoa
framework because that information is already on your hard drive or,
at most, an HTTP address away.
Still, because no single development history can naturally encounter
every topic and because exploring some topics in enough detail would
be too much of a digression from the story line, the last part of the book
consists of essays on important topics. They can be read in any order,
at any time.

1.4 RubyCocoa? That’s So Last Year!


During the writing of this book, various people suggested that it be
switched from RubyCocoa to MacRuby, Apple’s next generation of sup-
port for Ruby. As I write, though, MacRuby is still in beta. Both my lim-
ited experience with it and my subscription to the developer mailing list
make me think it’s not quite ready to replace RubyCocoa. As I noted in
the previous section, most of your time spent learning RubyCocoa will
be spent learning the Cocoa part. That’s the same in RubyCocoa and
MacRuby, so you might as well learn it in the more stable environment.
At some point, you’ll switch to MacRuby. If you like to be on the cut-
ting edge, you’ll do it soon. If not, it will be later. In either case, it
helps to know what’s coming. For that reason, I’ve written Chapter 25,
MacRuby, on page 334 for you.

1.5 Prerequisites
• You should have used a Mac enough that you’re familiar with the
conventions Mac apps follow. There’s no need to have ever built an
app with a graphical user interface, whether for the Mac or for any
other platform. You don’t need to understand Objective-C (or C).
• You should know Ruby reasonably well. A good measure of that is
whether you’re comfortable reading parts of someone else’s Ruby
code. If some gems’ behavior surprises you, do you follow a stack
trace into it to see what’s really going on?
I’ll use some tricky Ruby code behind the scenes, but the code
you’ll need to understand will be fairly straightforward. However, I
won’t stop to explain common idioms like this sort of initialization:
@var ||= 5

Report erratum
this copy is (P1.0 printing, July 2009)
P REREQUISITES 14

If you don’t think you know Ruby well enough, I recommend the
Pickaxe book, Programming Ruby [TFH08], possibly supplemented
with The Ruby Way [Ful06]. My own Everyday Scripting with Ruby
[Mar06] teaches Ruby in the same style as this book teaches Ruby-
Cocoa—by having you implement projects alongside the book—
but it may be too slow-paced for an experienced programmer, and
you’ll still want the Pickaxe book for reference.
• Make sure you’re running Apple’s version of Ruby. You can con-
firm that like this:
$ /usr/bin/which ruby
/System/Library/Frameworks/Ruby.framework/Versions/1.8/usr/bin/ruby

If you see other output (like /usr/local/bin/ruby or /opt/local/bin/ruby),


adjust your load path so that /usr/bin/ruby is used instead.
• You should be running Mac OS X 10.5 (Leopard) or later, with the
Developer Tools installed.1 Earlier versions of the Developer Tools
do not include RubyCocoa.
To see what version of RubyCocoa you’re running, type this to irb:
irb(main):001:0> require 'osx/cocoa'
=> true
irb(main):002:0> OSX::RUBYCOCOA_VERSION
=> "0.13.1"

I also have most of the examples write RubyCocoa’s version to the


console (visible via the Console app). If you manually installed a
version of RubyCocoa before you installed Leopard, that old ver-
sion may be loaded instead of Leopard’s (by an application, but
not by irb). If samples behave oddly, you check the console, and the
version is old, then delete /Library/Frameworks/RubyCocoa.framework.
RubyCocoa is available for earlier versions of OS X, but I’ve made
no attempt to avoid Leopard features. Moreover, the two main
Apple tools we’ll use (Xcode and Interface Builder) changed con-
siderably between 10.4 and 10.5. So if you install RubyCocoa on
a pre-Leopard version, prepare to spend time figuring out how a
picture in the text maps into an old tool.
• You have to be prepared to build the app yourself. If you just read
the book, the knowledge probably won’t stick. You’ll then find that

1. You had to choose to install the Developer Tools when you installed Leopard. If you
didn’t, you can fetch them off the install disc or from http://developer.apple.com.

Report erratum
this copy is (P1.0 printing, July 2009)
V ERSIONS 15

building your first app is a flood of tasks you vaguely know you
should perform but forget how. It’s better to build up your “muscle
memory” by building the book’s app before you build your own.
• You need to download bmrc-code.zip from http://pragprog.com/titles/
bmrc/source_code. It contains some files and tools you’ll need as
you work through the chapters. When you unzip bmrc-code.zip, it
will place all its contents in a code subdirectory. Since you’ll likely
want to rename that, I’ll leave off the code prefix when referring to
files. So, for example, when I direct you to the very first file you’ll
work on, I’ll refer to it as statusbar/most-basic-app.rb.
The download also contains snapshots of the app taken just before
and after each important step. As you work along, you can copy
snippets from the snapshots or use one of them as a starting point.
The download means that, at any given moment, there may be
thirty-four versions of the app on your disk: thirty-three interme-
diate versions that I supply and one that you’re working on. That
presents a problem. For example, on page 96, I write “look in Win-
dowController to see how it handles the AppChosen notification.”
The problem is that your version might not use the same names
as mine, so it might not handle anything called AppChosen. In that
case, you’ll need to look at my most recent version, not yours. But
which is most recent? You can find that out by looking backward
to the most recent code snippet that identifies its source file. The
following snippet, for example, would tell you we’re working on the
reshaped-with-dsl version of the app:
Download fenestra/reshaped-with-dsl/WindowController.rb

on_local_notification AppChosen do | notification |


@logWindow.title = notification[:app_name]
end

1.6 Versions
The book uses these tools:
• Ruby 1.8.6
• RubyCocoa 0.13.1
• Xcode 3.0
• Interface Builder 3.0

Report erratum
this copy is (P1.0 printing, July 2009)
O UR E XAMPLE A PP 16

Figure 1.1: Visible workings

These were the most recent versions delivered by Apple at the time of
writing.
When the book also uses libraries or gems, they’re included in the
book’s bmrc-code.zip file.

1.7 Our Example App


If you’re going to go to the trouble of working through an entire book of
code, you ought to end up with something more than knowledge at the
end of it. You ought to get code you can use, either as a complete app
or as snippets and templates to incorporate into your own apps. I’m not
creative enough to imagine an app with wide appeal, but I do know of
a template you might very well need.
You see, too many programmers are like the proverbial shoemaker’s
children who go unshod. You build sophisticated graphical interfaces
that let bond traders or camera buffs or physicists easily see and
manipulate the stuff of their work, but you don’t do the same for your-
self. A person who one moment is adding Ajax wizardry to streamline a
web app’s workflow will, the next moment, be trying to diagnose a bug
by groveling through textual log files, manually trying to reproduce the
steps to the failure, viewing the HTML source of page after page, and
poring over database tables that hold a distorted version of the app’s
objects. That doesn’t seem right.

Report erratum
this copy is (P1.0 printing, July 2009)
O UR E XAMPLE A PP 17

our RubyCocoa app


web app

Figure 1.2: An alternate GUI

It’s not right, and it’s our fault. We allow our apps to be childish. Every
parent knows how bad children are at answering the two vital ques-
tions: “All right, who did it?” and “What on Earth were you thinking to
make that seem like a good idea?” Trying to figure out a bug with noth-
ing more than a user’s report and the app’s regular GUI is like being
faced with the child who answers every question with “I dunno.” But
going after a bug with general-purpose tools like the language’s debug-
ger is like talking to the child who tries to get out of trouble by throwing
up a smoke screen of detail, irrelevancies, and finger-pointing. What we
need is to build every app with a special window into its inner workings
that programmers and testers can use (Figure 1.1, on the preceding
page).
The main example in this book will be a free-standing app that peeks
and pokes at another app through such a window. I’ll target a web app
in the book because that happens to be what I need right now, but
the same principle and much of the code would apply to any app. A
sketch of it in use is shown in Figure 1.2. It will contain a running log
of actions the web app has taken that is expandable to the desired level
of detail. A click of a button will tell the web app to undo or redo an
action. Our app, helped by the web app, will know when links refer to
domain objects (like user accounts), so the right gesture will pop up an
understandable, tweakable, and draggable representation of the object.
There’s much more that such an app could do, but since this is a book

Report erratum
this copy is (P1.0 printing, July 2009)
C ENTURIES OF THE B OOKMAKER ’ S A R T : S CORNED 18

about programming OS X, I’ll limit myself to features that teach Cocoa.


I think of such apps as windows you can both look and reach into, but
the word window is already taken, so I’ll use the Latinate equivalent:
fenestra. It’s a particularly apt choice because that’s also the word for
a hole surgically carved into a body part to let bad stuff leak out. In our
case, the “bad stuff” is information about bugs.
The act of creating such a hole is called fenestration. I’ll use that word
when I need to describe what the program is doing, and I’ll use fenestra
to describe the result.

1.8 Centuries of the Bookmaker’s Art: Scorned


I hate it when words refer to a figure that you have to flip the page to
see. It’s bad enough with drawings, but it really hurts my comprehen-
sion when the figure contains code. I’ve made a real effort to keep the
code and the references to that code on the same or facing pages. The
result is. . .

Report erratum
this copy is (P1.0 printing, July 2009)
S OME T ERMINOLOGY 19

. . . big blank spaces at the bottom of some pages. Text and figures are
traditionally laid out to avoid that ugliness. I embrace it. You deserve
an unattractive book.

1.9 Some Terminology


While writing the book, I sometimes had a choice between consistent-
but-awkward usage and flowing-but-inconsistent usage. For example,
consider the following bit of Ruby:
"foo".upcase

I’d normally say that Ruby “sends the message :upcase to the string
"foo".” Sometimes, though, the words sends and message won’t work
in a sentence, so I use “calling the method” instead. There’s nothing
but stylistic significance to the choice—I don’t mean a different thing.
Similarly, when writing of a variable, I might say that it “refers to,”
“names,” or “points at” an object. I might also say it “is” an object—
even though that’s strictly incorrect—because “i names 5” sounds silly.

1.10 Service After the Sale


My mail address is [email protected].
You can find errata at http://pragprog.com/titles/bmrc/errata.

1.11 Solving Problems


The Apple documentation (cited throughout the book) will be your main
source of Cocoa information, but don’t be surprised when you run into
problems that it doesn’t help you solve. Cocoa is big.
When I’ve been stumped, I’ve had the best luck just using Google to
search for the right keywords. A thoroughly gratifying percentage of the
time someone has written a blog entry or email message solving my
exact problem. The solutions are almost always in Objective-C, but I
expect that won’t be a problem for you after you finish the book.
There is a low-volume mailing list, https://lists.sourceforge.net/lists/listinfo/
rubycocoa-talk, where you can ask questions about RubyCocoa. The
main Cocoa developer mailing list, http://lists.apple.com/mailman/listinfo/
cocoa-dev, has much higher volume. If you can phrase your question

Report erratum
this copy is (P1.0 printing, July 2009)
A CKNOWLEDGMENTS 20

in terms that make sense to an Objective-C programmer, you can get


help there. It’s not unusual for Google to point me to its archive.
In /Developer/Examples, Apple provides examples of Cocoa features in
the form of small—but complete—apps. They’re written in Objective-C.
I am ever so gradually translating them into Ruby at http://github.com/
marick/cocoa-examples-translated. (I welcome help.)

When it comes to RubyCocoa itself, I’ve used both its source and tests
to answer my questions. I encourage you to download RubyCocoa from
http://rubycocoa.sourceforge.net.

1.12 Acknowledgments
Dawn, light of my life.
The creators of RubyCocoa: Eloy Duran, Fujimoto Hisa, Chris Mcgrath,
Satoshi Nakagawa, Jonathan Paisley, Laurent Sansonetti, Chris
Thomas, Kimura Wataru, and others.
Corey Haines, for spending two days of his Pair Programming Tour2 in
my living room, helping me figure out the mysteries of drag and drop.
My editor, Daniel Steinberg.
Technical reviewers Chris Adamson, Julio Barros, Craig Castelaz,
Michael Ivey, Jerry Kuch, Mathias Meyer, Allison Newman, and Scott
Schram.
Readers of the beta drafts: Steven Arnold, Jason M. Batchelor, Rune
Botten, Tom Bradford, Stephyn G. W. Butcher, Leroy Campbell, Gregory
Clarke, Eloy Duran, Frantz Gauthier, Joseph Grace, Aleksey Gureiev,
Christopher M. Hanson, Cornelius Jaeger, Masahide Kikkawa, Fred-
erick C. Lee, Jay Levitt, Tim Littlemore, Nick Ludlam, Stuart Malin,
Ule Mette, James Mitchum, Steve Ross, Peter Schröder, Jakub Suder,
Tommy Sundström, Matthew Todd, Daniel J. Wellman, Markus Werner,
“Dr. Nic” Williams, and perhaps others whose names I didn’t write
down. (Sorry.)
Although this is a book about RubyCocoa, I’ve snuck in bits and pieces
of a philosophy and pragmatics of application design. It’s a style I
have learned from people such as Kent Beck, Ward Cunningham, Carl
Erickson, Michael Feathers, Martin Fowler, Steve Freeman, Richard P.

2. http://programmingtour.blogspot.com

Report erratum
this copy is (P1.0 printing, July 2009)
A CKNOWLEDGMENTS 21

Gabriel, Andy Hunt, Ron Jeffries, Ralph Johnson, Joshua Kerievsky,


Yukihiro Matsumoto, Nat Pryce, Richard Stallman, Guy Steele, Prag-
matic Dave Thomas, and others. Without them, this book would have
been less interesting to write and—I hope—read.
Sophie Marick for the picture on page 16.
Giles Bowkett for the musical accompaniment to the embedded video
in the sample app’s help pages.
The baristas at Bar Guiliani, Aroma Cafe, and Espresso Royale, espe-
cially Alex Kunzelman for not calling the nice people from the mental
health center around the fourth draft of Chapter 7.

Report erratum
this copy is (P1.0 printing, July 2009)
Chapter 2

How Do We Get
This Thing Started?
We’re going to start fast, small, and with the fundamentals. To that end,
here’s the smallest RubyCocoa app:
Download statusbar/most-basic-app.rb

#!/usr/bin/env ruby

Ê require 'osx/cocoa'

Ë OSX::NSApplication.sharedApplication
Ì OSX::NSApp.run

If you run it, you’ll see that it does nothing but exist: no windows, no
output, no exit:
$ ruby most-basic-app.rb

(You’ll have to kill the script with Control - C .)


What causes this nonbehavior? Line Ê creates the ability for Ruby and
Objective-C methods to call each other. You’ll see more about how that
works throughout the book.
Line Ë’s NSApplication is the class corresponding to the entire applica-
tion itself. The call to class method sharedApplication creates the sin-
gle instance of that class, names it with the constant NSApp (used on
the next line), connects it to the window server, and does other useful
initialization.
A P ROGRAM T HAT P RINTS 23

The NS prefix is used by all the Cocoa classes you’re ever likely to see.
So, using the module prefix OSX:: isn’t really helping to avoid name
clashes. I’ll usually just include the OSX module and forget about it.
Notice that sharedApplication isn’t an idiomatic Ruby name. In Ruby,
you would be much more likely to see shared_application. It is idiomatic
Objective-C, though. You should expect to see such method names—
and even stranger ones—in RubyCocoa programs.
At Ì, NSApp is told to run. It does, waiting forever for someone to send
it work to do.

2.1 A Program That Prints


In this section, I’m going to make the app do one tiny additional thing:
print a message to standard output. That raises two questions right
away:
• When should the message be printed? Since the Cocoa runtime
tells NSApp when it (NSApp) has finished launching, that seems
like a good moment.
• Where do we add the code? In some systems, you’d add the code
in a subclass of NSApplication. That style is rare for Cocoa apps.
Instead, Cocoa programmers have NSApp delegate some of the
work to another object (called, unsurprisingly, a delegate).
The application structure we’ll use looks like Figure 2.1, on the next
page. Here’s the code:
Download statusbar/no-ui.rb

#!/usr/bin/env ruby

require 'osx/cocoa'
include OSX

Ê class AppDelegate < NSObject


Ë def applicationDidFinishLaunching(aNotification)
puts "#{aNotification.name} makes me say: Hello, world"
end
end

Ì our_object = AppDelegate.alloc.init
NSApplication.sharedApplication # Creates global NSApp
Í NSApp.setDelegate(our_object)
NSApp.run

Report erratum
this copy is (P1.0 printing, July 2009)
A P ROGRAM T HAT P RINTS 24

The Cocoa Runtime

Youʼve finished launching

NSApp

its
Weʼve finished launching delegate

Figure 2.1: Delegating work

The delegate is defined at Ê. It volunteers to handle the “application has


launched” event by defining the applicationDidFinishLaunching method (at
Ë). There are other events; because the class doesn’t contain a corre-
sponding method, it won’t have to handle them.
Notice what’s happening here: Objective-C, like Ruby, encourages duck
typing. The term comes from the saying “If it quacks like a duck, it’s a
duck.” If an AppDelegate object responds to the right messages, it’s a
suitable application delegate no matter what its declared superclass. It
does have to be an Objective-C object, so it’s declared as a subclass of
NSObject. That class is the root of the Objective-C class hierarchy, just
as Object is the root of the Ruby hierarchy.
The app creates the delegate at Ì. Whereas in Ruby you’d expect App-
Delegate.new, object creation in Objective-C is done in two parts. alloc
creates the object in memory and attaches all its methods to it. init is
what we in Ruby call initialize. Objective-C separates the two because
many Objective-C classes have variant init methods to support different
ways of initializing the instance.1

1. Ruby actually works like Objective-C under the covers: new first uses the class
method allocate and then sends initialize to the resulting instance.

Report erratum
this copy is (P1.0 printing, July 2009)
A P ROGRAM T HAT P RINTS 25

NSApp is told of its delegate at Í. Then NSApp starts running. Once the
application setup work is finished, NSApp calls its delegate’s application-
DidFinishLaunching method.

There’s not much more to the app: applicationDidFinishLaunching prints.


For fun, I had it print the name of its single argument, an NSNotification
object. Notice that sending a message to an Objective-C object is no
different from sending one to a Ruby object. (You can check that aNoti-
fication names an Objective-C object by printing its class: does it start
with NS?)
If you run the new script, you’ll see this:
$ ruby no-ui.rb
NSApplicationDidFinishLaunchingNotification makes me say: Hello, world

Try This Yourself


1. applicationDidFinishLaunching is not the only message that can be
sent to a delegate. It’s too early for you to handle most of them,
but try changing no-ui.rb to handle applicationWillFinishLaunching.2
2. Notifications have more than names. They can also point to an
object of interest. In the case of these two notifications, that object
is NSApp. Write some code to make sure that’s true. Use the object
message to get the object of interest.
3. Run your solution to the previous exercise again, but this time
misspell the word object. Learn to recognize the output—you’ll be
seeing it a lot in your RubyCocoa career. That’s what happens
when RubyCocoa tries to send any Objective-C message that the
object doesn’t respond to. It’s the equivalent of this Ruby error
message:
irb(main):005:0> notification.objct
NoMethodError: undefined method `objct' for #<Notification:0x10a4050>
from (irb):5

2. What’s the point of knowing an application hasn’t finished launching yet? Certain
things happen between the two events you know about. For example, it’s between them
that an application is told it was started by double-clicking a file. If you want to do any
setup before then, applicationWillFinishLaunching is the time to do it.

Report erratum
this copy is (P1.0 printing, July 2009)
P UTTING AN I TEM IN THE S TATUS B AR 26

2.2 Putting an Item in the Status Bar


Without using Interface Builder (described in Chapter 3, Working with
Interface Builder and Xcode, on page 37), making a user interface is
tedious work, so we will create only a single, incredibly simple user-
interface element in this section: an icon in the status bar (the symbols
and text on the strip across the top of the screen on the right).
Here’s the code:
Download statusbar/statusbar-item.rb

#!/usr/bin/env ruby

require 'osx/cocoa'
include OSX

class App < NSObject


def applicationDidFinishLaunching(aNotification)
Ê statusbar = NSStatusBar.systemStatusBar
Ë status_item = statusbar.statusItemWithLength(NSVariableStatusItemLength)

Ì image = NSImage.alloc.initWithContentsOfFile("stretch.tiff" )
Í raise "Icon file 'stretch.tiff' is missing." unless image

Î status_item.setImage(image)
end
end

NSApplication.sharedApplication
NSApp.setDelegate(App.alloc.init)
NSApp.run

Line Ê fetches a reference to the global status bar. Then line Ë allocates
screen space (on the left of all the other items) for the item you are
about to create. The parameter NSVariableStatusItemLength says that the
amount of space needed is unknown yet.
Line Ì uses a handy class that represents an in-memory image. The
next line, Í, quits the program if there was no image file to load. Its
unless check works because NSImage’s init follows the Cocoa conven-
tion of returning nil—rather than the allocated object—when something
goes wrong during initialization. There’s a suitable image file in status-
bar/stretch.tiff.

Finally, at Î, the image is placed in the previously allocated space.

Report erratum
this copy is (P1.0 printing, July 2009)
M ENUS 27

Try This Yourself


You can add text to the status bar with setTitle. Try that in statusbar-
item.rb, both with and without an accompanying image.3

2.3 Menus
Our status bar item doesn’t do anything, so let’s give it a menu. For
fun, I’ll use it to make the app speak to us. That’s not hard: I’ll use a
Cocoa object, NSSpeechSynthesizer, to turn text into speech.
Before starting that, let’s separate concerns. App will concern itself only
with application-wide events such as being launched and being termi-
nated. A new class, SpeechController, will do everything else.
Here’s the new version of App:
Download statusbar/speaking-statusbar.rb

class App < NSObject


def applicationDidFinishLaunching(aNotification)
statusbar = NSStatusBar.systemStatusBar
status_item = statusbar.statusItemWithLength(NSVariableStatusItemLength)
image = NSImage.alloc.initWithContentsOfFile("stretch.tiff" )
status_item.setImage(image)
Ê SpeechController.alloc.init.add_menu_to(status_item)
end
end

Only one thing has changed, at line Ê. We just create a SpeechController,


ask it to add its menu to the status bar item, and then forget about
it. Notice that a SpeechController is an Objective-C object—you can tell
because it’s created with alloc and init.
And here’s the SpeechController class:
Download statusbar/speaking-statusbar.rb

class SpeechController < NSObject


def init
Ê super_init
@synthesizer = NSSpeechSynthesizer.alloc.init
Ë self
end

Like App, SpeechController descends from NSObject. A SpeechController


needs to define its own init, though, because we want it to create an

3. If you’re not working in the statusbar directory, get a copy of statusbar/stretch.tiff from
there before running the script.

Report erratum
this copy is (P1.0 printing, July 2009)
M ENUS 28

NSSpeechSynthesizer and hold onto it in an instance variable. Such an init


method differs from Ruby’s familiar initialize in two ways:
Ê In an ordinary Ruby class, the initialize method uses super to call its
superclass’s initialize method. In an NSObject subclass, init calls the
superclass’s init method with super_init. (In general, any overriding
method method calls its superclass version with super_method.)
As you saw on page 26, init methods can sometimes return nil. For
that reason, a pedantically safe use of the superclass would look
like this:
return nil unless super_init

In this case, though, I know that NSObject’s init always returns self.
(In fact, it does nothing but return self, so I could omit the line
entirely.)
Ë In an ordinary Ruby class, initialize’s return value is irrelevant. In
contrast, an NSObject subclass must return self (or, in the case of
error, nil). If I’d forgotten line Ë, code like this:
s = SpeechController.alloc.init
s.add_menu_to(status_item)

. . . would make s an NSSpeechSynthesizer and then blow up on the


next line with a “no such message” failure. Even after seeing a
lot of those failures, it still sometimes takes me much too long to
think of blaming init.
Now for the menu. In Cocoa, a menu is represented by an NSMenu that
contains NSMenuItem objects. It’s those objects that receive “you’ve been
clicked” events from the window manager. If an NSMenuItem handles the
event, it forwards the work by calling an action method attached to a
target object. (See Figure 2.2, on the following page.)
The NSMenu itself does only a little work. It asks each item for its name
and key equivalent (the keystroke that selects that item via the key-
board instead of the mouse). Then it paints all the items on the screen.
SpeechController’s add_menu_to, shown in Figure 2.3, on the next page,
wires all this together.
It begins (Ê) by allocating an NSMenu object and attaching it to what-
ever container was given. This is another example of duck typing (and
a benefit of separation of concerns): this particular class doesn’t care

Report erratum
this copy is (P1.0 printing, July 2009)
M ENUS 29

The Cocoa Runtime

Youʼve been clicked

...

an NSMenu an NSMenuItem

...

a target object
Run that action method
(with an action method)

Figure 2.2: Clicking a menu

Download statusbar/speaking-statusbar.rb

def add_menu_to(container)
Ê menu = NSMenu.alloc.init
container.setMenu(menu)

Ë menu_item = menu.addItemWithTitle_action_keyEquivalent(
"Speak" , "speak:" , '' )
Ì menu_item.setTarget(self)

menu_item = menu.addItemWithTitle_action_keyEquivalent(
Í "Quit" , "terminate:" , 'q' )
Î menu_item.setKeyEquivalentModifierMask(NSCommandKeyMask)
Ï menu_item.setTarget(NSApp)
end

Ð def speak(sender)
@synthesizer.startSpeakingString("I have nothing to say." )
end
end
statusbar/speaking-statusbar.rb

Figure 2.3: Building a menu

Report erratum
this copy is (P1.0 printing, July 2009)
M ENUS 30

what it’s attached to, so long as that object responds to setMenu. Today,
it’s a status bar item. Tomorrow, it could be something else.
Next, an NSMenuItem is created and assigned to the menu by addItem-
WithTitle_action_keyEquivalent (line Ë). What’s up with that name? Objec-
tive-C has an interesting and nearly unique way of naming methods.
Here’s (almost) what Objective-C code that added a menu item would
look like:4
[menu addItemWithTitle: "Speak" action: "speak:" keyEquivalent: "" ]

The method being called here is named addItemWithTitle:action:keyEqui-


valent:. It takes exactly three arguments that have to come in exactly
the defined order.
RubyCocoa has to provide you with a way of naming that Objective-C
method. It can’t use the same name, because method names in Ruby
can’t contain colons. So, the colons are replaced with underscores. To
avoid excessive ugliness, you can leave off the last underscore, as I did
at line Ë.5
The first and third arguments to the method provide the name and key
equivalent. (This particular item has no key equivalent.) The second
argument is the name of the message to send when the menu item
is selected. Although the speak method is defined in Ruby, I’ve used
Objective-C’s notion of its name: "speak:". The name ends in a colon
because (as you’ll see shortly), speak takes a single argument.
Which object receives the speak: message is set on the next line (Ì). In
this case, the SpeechController handles the message itself.
Lines Í and Î show how you create a keyboard equivalent. Those
are almost never plain characters like q . They’re usually characters
with modifiers, like Command - Q . For whatever reason, the character and
modifier keystrokes are set in separate methods.
The menu item will send a terminate: message, but not to SpeechCon-
troller. Since it’s a message about the whole app, it’s targeted at NSApp
(line Ï), an Objective-C class that implements terminate:.

4. I’ve removed a little type casting because it’s not important to this explanation. To be
pedantic, the title and key equivalent shouldn’t be strings. They should be NSString objects,
which are written as @"string". Similarly, the action argument should be a “selector,” not
a string. You’ll see more—and more correct—examples of Objective-C later in the book.
5. That’s not always safe: consider an Objective-C class that has two methods, action
and action:.

Report erratum
this copy is (P1.0 printing, July 2009)
A N A PPLICATION B UNDLE 31

The speak (Ð) action is simple. Notice that it takes a sender argument,
which will be the NSMenuItem that was clicked. Action methods can use
the sender to query or change the user interface.
If you run the app, you’ll probably notice that the synthesizer takes a
second or two to start talking after you click the menu item. Presumably
it’s doing some first-time initialization. It’s more prompt the second
time.

Try This Yourself


1. Put this at the end of speak:
puts sender.objc_methods.grep(/title/i)

Use one or more of those methods to change the menu after some-
thing is said.
2. While terminating, NSApp will send its delegate two messages:
applicationShouldTerminate and applicationWillTerminate. The first lets
the delegate decide to cancel shutdown, and the second gives it a
chance to do any of its own cleanup.
Use applicationWillTerminate to print out “Goodbye, cruel world!”
3. Make applicationShouldTerminate return false unless the app has
spoken at least twice, true otherwise. See what happens when you
return values like nil, "fred", and the integer 0.
A small quirk: unlike the delegate messages you’ve seen so far,
applicationShouldTerminate takes an NSApplication as its argument,
so sender or app would be a better name than aNotification.
(If you need help, there’s a solution in statusbar/speaking-statusbar-
solution.rb.)

2.4 An Application Bundle


Fine though our script may be, it doesn’t behave like a Mac applica-
tion. If you double-click it, it doesn’t launch. (Most likely, it opens in
an editor.) It doesn’t get an icon in the Dock, you can’t see it if you
Command - Tab through open applications, and so on. In this section, I’ll
explain what’s special about apps. You’ll create your first one in Chap-
ter 3, Working with Interface Builder and Xcode, on page 37.

Report erratum
this copy is (P1.0 printing, July 2009)
A N A PPLICATION B UNDLE 32

Statusbar.app/

Contents/

Info.plist MacOS/ Resources/

Statusbar.icns rb_main.rb stretch.tiff

Figure 2.4: A bundle

On the Mac, executable code is delivered inside bundles. A bundle is


just a directory hierarchy with a certain predefined structure. Applica-
tions are one kind of bundle. If you look inside statusbar/Statusbar.app,
you’ll see a structure like that of Figure 2.4.6
Reading roughly top to bottom and left to right, we have these files:
Contents/
This identifies the bundle as a “modern” bundle.
Info.plist
This contains various configuration options. For example, if you
launch the application, you’ll notice that it doesn’t have a main
menu and doesn’t appear in the Dock. I made that happen by
setting LSBackgroundOnly. Apple’s Runtime Configuration Guidelines
[App08x] has the gory details about all the options you can tweak.
MacOS/
There is a small compiled Objective-C executable named Statusbar
in this directory. It loads and starts the Ruby code. (You don’t
have to write the Objective-C yourself; Apple’s Xcode, explained in
Chapter 3, Working with Interface Builder and Xcode, on page 37,
creates it for you.)

6. If you’re browsing from the command line, Statusbar.app looks like what it is: a direc-
tory. If you’re browsing with the Finder, it appears to be a single file. That’s because it’s a
package, a special kind of directory that the Finder pretends is a file. All application bun-
dles are packages. You can tell Finder to let you look inside it by selecting Show Package
Contents from Statusbar.app’s context menu.

Report erratum
this copy is (P1.0 printing, July 2009)
A N A PPLICATION B UNDLE 33

Resources/
This directory contains unchanging information the application
might use. The good thing about resources is that their loca-
tion is relative to the bundle itself, so code doesn’t need to use
absolute pathnames or know where it has been installed. Apple’s
Resource Programming Guide [App08v] teaches how to load and
use resources.
Because this is a small program, it has few resources:
Statusbar.icns
.icns files contain the icons shown in the Finder, Dock, and so
on. I create icon files with a drawing program and Icon Com-
poser, which you can find in /Developer/Applications/Utilities.
rb_main.rb
All your Ruby source files are stored as resources.
stretch.tiff
Pictures, sound files, movies: all these are stored in Resources.
For more information about bundles, see Apple’s Bundle Programming
Guide [App08d].

Ruby Code Within a Bundle


Our existing script barely needs to change when moved into a bundle.
Its name changed to rb_main.rb. (That’s not required, but it’s easiest to
follow the convention.) The following old line of code won’t work:
Download statusbar/speaking-statusbar.rb

image = NSImage.alloc.initWithContentsOfFile("stretch.tiff" )

That line assumes the script is running in the same directory as the
image file. That’s not true for an application, which should fetch the
image from Resources. That’s done like this:
Download statusbar/Statusbar.app/Contents/Resources/rb_main.rb

image_name = NSBundle.mainBundle.pathForResource_ofType('stretch' , 'tiff' )


image = NSImage.alloc.initWithContentsOfFile(image_name)

Simple enough.

Try This Yourself


1. What’s a running application’s working directory? You can print it
to the system log with this line:
NSLog(Dir.pwd)

Report erratum
this copy is (P1.0 printing, July 2009)
A N A PPLICATION B UNDLE 34

Add a menu item to Statusbar.app/Contents/Resources/rb_main.rb to


do that. You can view the system log with the Console app (in
/Application/Utilities). It will appear in the system.log log file.

Log the directory both when double-clicking the app and when
opening it from the shell like this:
$ open Statusbar.app

2. What does the process environment look like when the app is
launched by double-clicking (NSLog(ENV.inspect))?
You should see that it’s pretty sparse, containing nothing you set
in your .bashrc file. Therefore, the common gem-loading trick of
setting the environment variable RUBYOPT to rubygems won’t work
for a RubyCocoa app. Here are three solutions:
a) Just use require ’rubygems’ in your Ruby code. This is probably
the best solution. In Leopard, RubyGems is guaranteed to be
installed.
b) Create a file named ~/.MacOSX/environment.plist. (Note that the
directory starts with a period so that the Finder ignores it.) In
it, place this XML:
Download statusbar/environment.plist

<?xml version="1.0" encoding="UTF-8" ?>


<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN"
"http://www.apple.com/DTDs/PropertyList-1.0.dtd" >
<plist version="1.0" >
<dict>
<key>RUBYOPT</key>
<string>rubygems</string>
</dict>
</plist>

You will have to log out and log back in for the change to take
effect. Once you do, the environment variable will be set for
all applications.
c) Add the following lines to Info.plist:
<key>LSEnvironment</key>
<dict>
<key>RUBYOPT</key>
<string>rubygems</string>
</dict>

Report erratum
this copy is (P1.0 printing, July 2009)
W HAT N OW ? 35

Beware, though: Info.plist is used only if your app is launched


through Launch Services. The Finder and the shell’s open
command use Launch Services, but your IDE or program-
mer’s editor may not.7 In particular, Apple’s Xcode does not.

2.5 What Now?


Given what you’ve seen, I hope you believe that writing a Mac app in
Ruby is potentially as pleasant as any other Ruby programming. But
only potentially. Three obstacles still have to be removed:
• Setting up even simple user interface elements like menus seems
like fiddly, detail-heavy work. Imagine what windows with panels
and sidebars and tooltips must be like! Apple’s free developer tools
remove that obstacle. They’re explained in Chapter 3, Working with
Interface Builder and Xcode, on page 37.
• The code has already used a number of mystery classes such as
NSMenu, NSBundle, and NSImage. How do you find, understand, and
use their documentation? That’s explained in Section 3.2, The API
Browser, on page 49.
• Information about classes and methods is all well and good, but
classes and methods exist in a context. You need to know how
Mac applications are put together and what kinds of things they
can do. That’s the topic of most of the rest of the book.

7. See Apple’s Launch Services Programming Guide [App08o] for more.

Report erratum
this copy is (P1.0 printing, July 2009)
Part I

A First Realistic App


Chapter 3

Working with
Interface Builder and Xcode
In this chapter, we’ll build a simple GUI that lets us fenestrate an app
(open a window, or fenestra, into its internals). It’s the acorn that will
grow into the mighty oak tree of Section 1.7, Our Example App, on
page 16. It looks like Figure 3.1. We’ll imagine we’ll type the name
of the application we want to fenestrate in the smaller text field, and
information from that app will ooze into the larger text view.

Pick an app:

Figure 3.1: An app with input and output


T HE B ASICS 38

3.1 The Basics


The two main tools for building Mac apps are Xcode and Interface
Builder. (The latter is often abbreviated IB.) Xcode manages the col-
lection of files used to build an app and provides a programmer’s edi-
tor. It’s akin to Eclipse or IntelliJ IDEA for Java, but it’s tailored to
Objective-C programs. Interface Builder is a tool for drawing executable
user interfaces.
Begin by creating a project. Start Xcode (in /Developer/Applications). If
you see a Welcome page, dismiss it (although you may want to look at
it later). Create a project by selecting File > New Project. You’ll see a
screen like this:

Choose, as I did in the figure, a Cocoa-Ruby application, and hit Next.


You’ll be asked to name the project. Since you’re also naming the app,
it’s conventional to pick a capitalized name. I picked “Fenestra.”

Report erratum
this copy is (P1.0 printing, July 2009)
T HE B ASICS 39

After you hit Finish, you’ll see something like the following:

This view has nothing to do with the file system structure of the project.
It’s more like a collection of smart folders in the Finder or iTunes. I
won’t give a detailed description of what you see, but notice some files
we edited in Section 2.4, An Application Bundle, on page 31: Info.plist
and rb_main.rb. Those are the source versions of the files that are put in
the application bundle when it’s built.
Click Build and Go on the toolbar now. After a bit of a pause, you
should see this window:

Although you’ve written no code, your app already does some of what
a real app does. You can hide and show it, minimize and zoom it, and
quit it by either using the menu or pressing Command - Q . Quit it now.

Report erratum
this copy is (P1.0 printing, July 2009)
T HE B ASICS 40

Our next job is to make that window have the label, text field, and text
view shown in Figure 3.1, on page 37.

Interface Builder
In the project view, there’s an entry in the right panel called Main-
Menu.nib. You can also see it under the Resources or NIB Files groups
in the left panel. (If you see MainMenu.xib instead, don’t worry; it’s the
same data, just formatted differently.)
You can think of a nib file 1 as describing a user interface, but the
reality is more clever: it’s actually a “frozen” (“marshaled” or “serial-
ized” or “pickled”) user interface. For more about that cleverness, see
Section 11.2, Archiving, on page 134 and Section 14.4, bind_toObject_
withKeyPath_options, on page 192. For now, edit the nib file by double-
clicking its name.
You should see the following five windows, although sized and placed
differently. (If you don’t see all the windows, try selecting Window >
Bring All to Front.)

① ④ ⑤

• The main menu is what appears in the menu bar on top of the
screen. You’ll be tinkering with that in Chapter 22, Fit and Finish,
on page 287.

1. The name stands for “name’s irrelevant, basically,” although some claim it stands for
“NeXT Interface Builder.”

Report erratum
this copy is (P1.0 printing, July 2009)
T HE B ASICS 41

• The main window is what the window will look like in the running
app.
• The doc window (or document window) represents the contents of
the nib file in the same way that a window in Pages or Word repre-
sents the contents of a file. The doc window is a Finder-like view
of the objects most important to the user interface. We won’t be
using all of them, and I’ll describe only those we do. A good place
to look for descriptions is in Apple’s Human Interface Guidelines
[App08b].
The doc window starts out using icons, but hereafter I’ll show it
in list view because that lets me save some space in figures. I use
list view in my ordinary programming, too—as the UI gets more
complicated with objects within objects within objects, list view
makes working with them easier.
• The library contains a large set of predefined user interface ele-
ments. Shortly, you’ll be dragging three of them onto the main
window. Dragging is how you build a Cocoa user interface with
Interface Builder.
• The inspector is a tabbed editor for the bazillion-and-two things
you can change about each UI element.
To begin, use the search box at the bottom of the library’s window to
search for text. One of the results will be an element named Label, as
shown in the following images. Drag it into the top-left corner of the
main window. Note that as you get close, guide lines will appear to help
you put it an Apple-approved distance from the edges of the window.

Report erratum
this copy is (P1.0 printing, July 2009)
T HE B ASICS 42

After you drop the label, double-click it to edit its text. Change it to
“Pick an app:” or whatever you like.
The library will also contain text fields and text views. Drag them into
the window. Note that, when selected, they have drag handles that let
you resize them. Make a window that looks something like the following:

Big views have little views...


...in front of them to hide ’em. And little views have lesser views, and so
ad infinitum.2
Everything you’ve done has involved two main classes of object. First,
there’s an NSWindow that represents a rectangular area on the screen.
Within it are different subclasses of NSView, each responsible for its own
piece of the window. Views are typically nested, with smaller views “on
top of” larger ones (which means that they are responsible for the space
they obscure).

2. With apologies to Augustus De Morgan and Jonathan Swift.

Report erratum
this copy is (P1.0 printing, July 2009)
T HE B ASICS 43

Once you’ve put IB’s doc window in list mode, you can see the view
structure of your window by expanding the NSWindow:

• The content view covers the entire space of the window. It contains
all the other views.
• The label and text field cover part of the content view. Notice
that they are both NSTextField objects—their different appearance
is entirely because of how they’re initialized. (See Section 3.5,
Attributes, on page 58, for more.)
• What seems like a simple text view is actually its own hierarchy of
objects. An NSScrollView contains the actual NSTextView and also two
scrollers. One of them (the vertical scroller) takes up some space
even when there’s no need for a scrollbar, but the other is invisible
until it’s needed.
• If there were other visible objects in the window, even ones as
insignificant as a vertical line used as a separator, they’d be NSView
objects too. (A line is an NSBox, just a very, very thin one.)
You’ll eventually need to know more about views to answer questions
like “What object handles a mouse click?” and “What object handles
keypresses?” This book will answer those questions only in the con-
text of Fenestra. For complete details, see Apple’s Cocoa Event-Handling
Guide [App08h].

Report erratum
this copy is (P1.0 printing, July 2009)
T HE B ASICS 44

Connecting the Interface to Code


In the working application, typing into the text field will make a connec-
tion to a web app that will spew data for Fenestra to catch and display
in various pleasing ways. For this first example, though, let’s just have
the text view echo whatever is typed into the text field.
If you squint, that looks a lot like the earlier status bar example (Sec-
tion 2.3, Menus, on page 27). In it, some input (a mouse click in a menu)
went to an action, a method inside the target class (SpeechController).
That action did almost no processing; it just sent text to some Cocoa
object attached to an instance variable. Like this:

Speak
class SpeechController < NSObject
Quit
...
def speak(sender)
@synthesizer.startSpeakingString(...)
end
...
end

In that code, @synthesizer is a particular kind of instance variable: one


that points to some Cocoa object used for output. In the jargon, that’s
an outlet.
The connections shown earlier were made with code we wrote, code like
this:
menu_item = menu.addItemWithTitle_action_keyEquivalent(
"Speak" , "speak:" , '' )
menu_item.setTarget(self)

. . . and this:
@synthesizer = NSSpeechSynthesizer.alloc.init

That kind of code is boring to write. Interface Builder can usually elim-
inate the need for it. All you need to do is create objects and draw lines
between them. The objects and wiring instructions are stored in the nib
file and decoded when the app starts up.
1. We already have almost all the objects that need to be wired to-
gether: you can see them in the main window and the doc window.
Those are all UI objects, though, and we need one more to serve
as the target of actions, the so-called controller.

Report erratum
this copy is (P1.0 printing, July 2009)
T HE B ASICS 45

The way you make an object in Interface Builder is by dragging


some representation of it from the library. Since our class doesn’t
exist yet, it’s not in the library. But no matter what the details,
any object made in Interface Builder has to be an NSObject—all
Cocoa objects are. So, we can use that as a placeholder. Search
for NSObject in the library. When you find it, drag it into the doc
window, as shown here:

2. Now we can add detail. With the new object selected, pick the
Identity (sixth) tab in the inspector. The result should look like the
following:

Report erratum
this copy is (P1.0 printing, July 2009)
T HE B ASICS 46

The Class Identity (topmost) field is where we tell IB about the


class of our object. Controller class names conventionally end in
Controller. Since we’ll have only one for now, let’s just call it Con-
troller. Type that in the field. Notice that the name changes in the
doc window after you hit Return .
3. In the Class Actions field, add a new action (using the + but-
ton). Name it chooseApp:. You have to end with the colon, since
IB thinks the action is an Objective-C method that takes a single
sender argument.

The Type field is the type of the sender argument. A type of id


means “figure it out at runtime,” which both Ruby and Objective-
C are perfectly happy to do. So, leave it as is.
4. In the Class Outlets field, add an outlet named log. As with the
chooseApp: action, there’s no need to change the type from id.

The inspector should now look like this:

Interface Builder now knows that Controller exists (or will exist) and
needs two connections.

Report erratum
this copy is (P1.0 printing, July 2009)
T HE B ASICS 47

1. First, open the Controller’s Connections (fifth) tab in the inspector.


That looks like this:

2. Our outlet and action show up there. Their lines have little circles
at the end. If you click the one for the log outlet, you can drag a
line to the text view in the main window, as shown in the follow-
ing figures. Make sure to drop the end of the line in the “Lorem
ipsum” text; if you drop it below there, you’ll actually be making
a connection to the scroll view that contains the text view. Check
the tooltip to make sure.

In IB 3.0, the inspector loses track of what it’s inspecting when you
drop the far end of the connection. Worse, clicking the Controller in
the doc window doesn’t get it back. What I do is click some other
object (like the text view) and then click the Controller again. (Later
versions of IB don’t have this problem.)

Report erratum
this copy is (P1.0 printing, July 2009)
C REATING AND E DITING C LASSES IN X CODE 48

Once you’ve made the connection correctly, the log entry in the
Connections tab will now describe the other end as “Text View,”
as shown here:

If you made a mistake, you can destroy the connection by clicking


the little x. Double-clicking the now-filled-in circle will take you to
the other end of the connection.
3. Next, drag the chooseApp: received action to its source in the text
field.
IB now knows how Controller should be hooked into the UI. There’s no
code for that class yet, though. We’ll write it in Xcode. Save the nib file
with Command - S before switching from IB to Xcode.

3.2 Creating and Editing Classes in Xcode


In Xcode, select the File > New File menu item. You’ll see this dialog
box:

Report erratum
this copy is (P1.0 printing, July 2009)
C REATING AND E DITING C LASSES IN X CODE 49

Select the Ruby NSObject subclass. Name the new file Controller.rb. Al-
though that’s unidiomatic Ruby, it seems to make Xcode happier.
When that’s finished, you’ll see something like this:

(The comment at the head of the file will look different. If you want to
peek ahead and see how to make it include your name and company
name, see Section 22.6, The About Window, on page 297.)

The API Browser


I’m about to walk you through the implementation, telling you which
methods to call on which classes as we go. Because of that, you don’t
need to know how to use the Cocoa API browser to find classes and
methods yet, but you may want to anyway.

Report erratum
this copy is (P1.0 printing, July 2009)
C REATING AND E DITING C LASSES IN X CODE 50

The browser is available by selecting Help > Documentation. It looks


like this:



The arrows point out the parts of the browser I find most helpful:
1. I use the search field to find documentation for classes and meth-
ods whose name I know. To go from “I need to do X ” to ”I need
to use class Y,” I use Google. I find it does a better job of finding
relevant hits in Apple non-API documentation than does Xcode’s
search or the one at Apple’s Developer Connection website.3
2. If you have a similar experience (which you might not), you can
restrict search results to the API with the button on the far left
of this bar. Toward the middle, there’s an All Languages button,
which means in practice “include the Java API.” That’s not useful,
so I turn it off.
3. In the middle of this bar, there’s a drop-down list that contains
the class name. If you open it, you’ll get quick access to instance
and class methods.
At the right, marked with a “C,” you can get quick access to super-
class and subclass documentation.

3. http://developer.apple.com/

Report erratum
this copy is (P1.0 printing, July 2009)
Other documents randomly have
different content
pensée, il n'a pu cependant y échapper. Il est le fils du XVIIIe siècle.
Avec sa foi dans le progrès indéfini du genre humain, c'est une
bouture de Condorcet. Mais—disons-le à son éloge!—le XVIIIe siècle,
dont il procède, n'a pu lui donner ce mépris de brute pour les
problèmes surnaturels qui distingue ses plus beaux génies. Dieu,
l'âme, son essence et ses destinées, les hiérarchies spirituelles, etc.,
sont restés des questions pour Jean Reynaud, et des questions que
le panthéisme contemporain ne résoud pas. En vertu de son genre
d'intelligence, la notion théologique n'a donc pas été abolie en lui,
mais seulement obscurcie et faussée. Et voilà justement ce qui a
produit, sous la plume de ce philosophe singulier qui a le coup de
marteau de la théologie, un chaos également monstrueux pour les
théologiens et pour les philosophes! Voilà pourquoi il a mutilé, au
nom de la théologie, le triple monde que la théologie enseigne, et
qu'il le réduit à un seul dans son livre, malgré son double titre de
Terre et Ciel!

En effet, pour qui sait l'embrasser et l'étreindre, ce livre, au fond,


n'est autre chose qu'une mutilation et un renversement des idées
chrétiennes. C'est notre Credo pris à rebours et fondé sur la pluralité
des mondes éternels, sans royaume des cieux et sans enfer. Telle, en
deux mots, la conception théologique du livre de Jean Reynaud;
mais ce n'est pas tout au détail. L'auteur de Terre et Ciel a beau s'en
défendre, il n'est réellement qu'un panthéiste de notre temps, sous
les guenilles de tous les hérétiques de ce moyen âge contre lequel il
se permet tant de mépris. N'oublions pas que son livre n'est, avant
tout et après tout, qu'un essai de cosmologie... Parti du cosmos pour
aller au cosmos, en passant sur le cosmos, l'auteur s'agite, mais
stérilement, pour organiser plus qu'un cimetière... Le mot de Ciel est
de trop dans le titre de son ouvrage, et la Terre même comme il la
conçoit n'est pas la notion chrétienne de la terre. Ce n'est plus le lieu
de l'expiation et de l'épreuve, le champ de mort d'où une chrysalide
de cent cinquante milliards d'âmes doit un jour se déployer et
s'envoler dans les cieux. Cette double notion de la terre et du ciel, la
seule que puissent admettre également l'intelligence des penseurs et
l'imagination des poètes, Jean Reynaud, théologien agrandi par la
philosophie, l'a réputée mesquine, enfantine et débordée par ce
triomphant Esprit humain, qui a le droit d'exiger mieux. Seulement,
pour la remplacer, cette notion inférieure et grossière, l'éminent
inventeur n'a trouvé rien de plus puissant que de ramasser, dans la
poussière des rêves de l'humanité les plus rongés par les siècles et
les plus transparents de folie, le système ruminé par l'Inde—cette
vache de la philosophie—d'une métempsycose progressive, qui met
l'homme aux galères à perpétuité de la métamorphose et son
immortalité en hachis!

Au moins, pour expliquer de cette façon le problème surnaturel de


l'homme et de sa destinée, pour revenir, en plein XIXe siècle,—après
les travaux philosophiques de Hegel et de Schelling,—à ce risible
système de la métempsycose, digne tout au plus d'inspirer une
chanson au marquis de Boufflers ou à Béranger, qui l'a faite, fallait-il
se sentir une force d'induction et de déduction irrésistible; fallait-il
que la grandeur des facultés philosophiques sauvât la misère du
point de vue que l'on ne craignait pas de relever. Et c'est ici qu'après
la question du point de vue, général et dominateur, qui emporte
l'honneur d'un livre en philosophie, devait se poser la question du
talent et de ses ressources, qui couvre l'amour-propre de l'auteur. Eh
bien, nous le disons en toute vérité et sans vouloir y faire de
blessures, l'amour-propre de Jean Reynaud ne sera pas couvert! Une
fois le fond du livre écarté, les qualités qui resteront pour le
défendre n'imposeront point par leur éclat aux véritables
connaisseurs. Et nous ne parlons pas encore ici de la forme la plus
extérieure de ce livre, de sa conformation littéraire. Nous restons
métaphysicien. En métaphysique, il sera très facilement constaté,
par tous ceux qui ont l'habitude ou l'amour de ce genre de
méditation, que les tendances de Reynaud sont plus vives et plus
fortes que ses facultés.

Le traité de Terre et Ciel, qui résume toute sa vie intellectuelle, car il


a été effeuillé dans des revues et des journaux depuis dix ans, ce
traité, regardé comme un système à toute solution par un petit
nombre de gens solennels et mystérieux qu'on pourrait appeler les
Importants de la philosophie, est, qu'on nous passe le mot (le seul
qu'il y ait, hélas! pour exprimer notre pensée)! un perpétuel coq-à-
l'âne sur les relations du temps à l'éternité. Pour un métaphysicien,
qui doit connaître les éléments de la science qu'il cultive et n'avoir
pas de distractions, Jean Reynaud est entièrement étranger à la
conception de l'éternité, ou, s'il la pose parfois, il l'oublie. C'est qu'au
fond il n'a rien de net, de ferme, de péremptoire et d'arrêté dans
l'esprit. Il patauge.

«L'infinité,—dit quelque part ce panthéiste malgré lui ou à dessein


(lequel des deux?),—l'infinité est un des attributs de l'univers.» Mais
l'infinité est le contraire de la mesure, comme l'éternité est le
contraire du nombre! Des écoliers sauraient cela. Et voyez la
singulière conséquence: si l'on met l'infini à la place de l'étendue, où
pose-t-on l'axe du monde et que devient pour Jean Reynaud cette
gravitation dont il est si sûr et si fier? Dans le chapitre de l'Homme,
où le récit de la Genèse est culbuté par l'hypothèse, l'éternelle
hypothèse du développement progressif de la vie et de «la création
graduelle», Jean Reynaud méconnaît l'Absolu divin. Il semble ignorer
que Dieu soit un acte pur, et ce que c'est même qu'un acte pur! Il
s'imagine que Dieu, comme l'homme, a son chemin à faire et qu'il a
besoin d'expérience... Ce manque de précision, qui, en
métaphysique, se mue si vite en erreur ou s'étale si pompeusement
en bêtise, on le signalerait à toutes pages dans le livre de Terre et
Ciel si on ne craignait pas de fatiguer le lecteur par des citations trop
abstraites.

Ainsi donc, en nous résumant, nous trouvons, à côté de la donnée


vicieuse et puérile du livre de Jean Reynaud, des qualités
métaphysiques d'un degré inférieur, sans pureté et sans force réelle,
un langage trouble toujours et souvent contradictoire. Le traité de
Terre et Ciel est une petite Babel bâtie par un seul homme. C'est la
confusion des langues de plusieurs sciences, qui se croisent et
s'embrouillent sous la plume pesante de l'auteur. Sa pensée ne
domine pas tous ces divers langages et ne les fait pas tourner
autour d'elle, avec leurs clartés différentes, dans la convergence de
quelque puissante unité. Théologien de prétention malgré son
caractère philosophique, théologien quiquengrogne en philosophie, il
peut avoir beaucoup lu les théologiens catholiques, mais il n'a point
de connaissances accomplies, lumineuses, en théologie; car, s'il en
avait, aurait-il épaulé le système du progrès indéfini de Condorcet
avec la métempsycose de Pythagore?... Aurait-il pu jamais adopter
comme vrai ce système du développement progressif de la vie et de
ses perpétuelles métamorphoses, qui parque l'homme sur son globe
et applique à la création tout entière, à l'œuvre du Dieu tout-
puissant, lequel a créé spontanément l'homme complet, innocent et
libre, ce procédé de rapin qui, par des changements imperceptibles
et successifs, se vante de faire une tête d'Apollon avec le profil du
crapaud? Le sophisme épicurien, le plus compromis des sophismes
grecs, qui donnait à la Divinité la forme de l'homme parce qu'on n'en
connaît pas de plus belle, est le genre de preuves le plus familier de
Reynaud. Ne comprenant jamais l'action divine que comme il
comprend l'action humaine, l'auteur de Terre et Ciel se croit fondé à
tirer une impertinente induction de nous à Dieu, et cet abus de
raisonnement, qui revient dans son livre comme un tic de son
intelligence, produit pour conséquence de ces énormités qui coupent
court à toute discussion. Pour n'en citer qu'un seul exemple, Jean
Reynaud exige la pluralité des mondes ou il n'admet pas Dieu, parce
que (ajoute-t-il avec un sérieux qui rend la chose plus comique
encore), sans la pluralité des mondes, Dieu est évidemment «lésé
dans son caractère de créateur». On conçoit, n'est-il pas vrai?
qu'après des affirmations de cette nature un homme sensé ne
discute plus.

Nous avons, nous, à peine discuté. Nous ne pouvions, ni pour le


public ni pour nous, ni pour le livre même dont il s'agit, l'examiner
dans le détail trop spécial, trop technique, des nombreuses
questions qu'il soulève; mais le peu que nous avons dit suffira. Si ce
singulier traité de philosophie religieuse, qui essaie de renverser tous
nos dogmes, sans exception, sous l'idée chimérique des
transformations éternelles et successives de l'humanité et sous un
panthéisme plus fort que l'auteur et qui le mène et le malmène; si ce
traité brillait au moins par une exposition méthodique, nous aurions
pu donner le squelette de ce mastodonte de contradictions et
d'erreurs. Mais Jean Reynaud n'a point de méthode. Son livre de
Terre et Ciel est une conversation, à bâtons rompus, entre un
philosophe théologien de l'avenir,

C'est moi-même, messieurs, sans nulle vanité!

et un pauvre théologien catholique (et je vous demande si le


catholicisme est bien représenté!), lequel laisse passer fort
respectueusement toutes les bourdes, dirait Michel Montaigne de
l'auteur de Terre et Ciel, absolument comme on laisse passer, en se
rangeant un peu, les boulets de canon auxquels il est défendu de
riposter. Vieux livre sous une peau nouvelle, l'ouvrage de Jean
Reynaud a emprunté jusqu'à sa peau. En effet, c'est l'opposition et
la caricature de ces Soirées de Saint-Pétersbourg dans lesquelles
l'auteur esquive aussi la difficulté d'une exposition méthodique par
cette forme trop aisée du dialogue, mais, du moins, en sait racheter
l'infériorité par l'éclat de la discussion, le montant de la repartie, la
beauté de la thèse et de l'antithèse et une charmante variété de
tons, depuis la bonhomie accablante du théologien jusqu'à la
sveltesse militaire; depuis l'aplomb du grand seigneur qui badine
avec la science comme il badinerait avec le ruban de son crachat
jusqu'au génie de la plaisanterie comme l'avait Voltaire.
Malheureusement l'esprit de Jean Reynaud n'a pas, lui, toutes ces
puissances. Il est monocorde, et la corde sur laquelle il joue n'est
pas d'or. Ses longues dissertations dialoguées, que ne brise jamais le
moindre mot spirituel, manquent profondément de vie, d'animation,
de passion enthousiaste ou convaincue, et elles nous versent dans
les veines je ne sais quelle torpeur mortelle. On dirait le procédé
Gannal appliqué à notre esprit tout vivant. Désagréable sensation!
Au milieu de cette logomachie théologique, si incroyablement
obstinée et dans laquelle pourtant exclusion est faite des miracles,
de la virginité, des sacrements, de l'idée de famille, il n'y a de clair,
pour qui sait voir, que la haine de Jésus-Christ sous le nom de
moyen âge. Seulement cette haine entortillée, insidieuse, nous fait
payer par un ennui à nous déformer la figure les embarras de la
pensée de l'auteur. Ah! qu'on aimerait mieux un peu de passion
franche, et, comme disait Shelley, l'athée, «que le serpent, une
bonne fois, se dressât sur sa queue et sifflât tous ses sifflements».
Au lieu de ces longueurs indécises, de ces toiles d'araignée
philosophiques, de cette mosaïque de filandreuses dissertations, qui
se lèvent par plaques sous les pieds de l'esprit et qui en retardent la
marche, qu'on aimerait mieux quelques lignes de conclusion, nettes
et courageuses, les articles (enfin arrêtés) du Symbole de la
philosophie, de ce Symbole qu'on nous jetterait à la tête, à nous les
arriérés, comme les Apôtres eurent autrefois l'impudence sublime de
jeter le leur, en bloc, à la tête du genre humain!

Mais rien de tout cela. Le livre de Jean Reynaud est et reste tout
simplement une hypothèse, qu'on propose, mais qu'on n'impose
pas... Ils savent très bien risquer le faux, les philosophes, mais ils ne
sont jamais assez sûrs que le faux qu'ils risquent est le vrai pour
avoir l'aplomb d'en faire un symbole. Ceci n'est réservé qu'aux
prêtres. Nous l'avons dit déjà, ce traité de Terre et Ciel, qui n'a de
grave que le ton, agrandit vainement et cache mal, sous le trompe-
l'œil des détails scientifiques, une théorie qui, réduite à ses plus
simples termes, n'est que ridicule et... immorale; car voilà son côté
sérieux! La métempsycose, ou la transformation successive de
l'humanité, emporte la morale humaine dans sa visible absurdité. Si
cette transformation qui recommence toujours est en effet la loi du
monde, tous les crimes et même l'assassinat ne sont plus que des
dérangements de molécules qui sauront toujours bien se
reconstituer, et l'affreux poète du suicide avait bien raison quand il
chantait:
De son sort l'homme seul dispose!
Il a toujours, quand il lui plaît,
Dans la balle d'un pistolet,
La clef de sa métamorphose!

Telle est la conclusion que les hommes pratiques tireront de la


doctrine du philosophe. Assurément, on doit espérer que de si
dégradantes conséquences, une fois seulement indiquées,
diminueront un peu dans l'opinion l'importance que le parti
philosophique antichrétien veut créer au livre de Jean Reynaud.

Et qu'on nous permette d'ajouter encore un dernier mot.

Quand on s'élève à une certaine hauteur, il n'y a plus que deux


sortes de livres,—deux grandes catégories, dans lesquelles tous les
genres et tous les sujets peuvent rentrer: les livres faits par
l'observation et les livres faits par la rêverie. Observation et rêverie,
voilà les tiges-mères de toutes les familles de l'esprit humain. Eh
bien, ni comme observateur ni comme rêveur Jean Reynaud
n'occupera une place élevée dans la hiérarchie des intelligences de
son temps! Tout au plus donnera-t-il le bras à Pierre Leroux, l'auteur
de l'Humanité, avec lequel il a plus d'une analogie, et s'en iront-ils
tous deux à la fosse commune de l'oubli. Observateur nul, puisque
son système n'est qu'une induction, et rien de plus, il choque
profondément en nous la faculté qui a soif de réalités et de vérité,
mais il n'intéresse pas l'imagination davantage. Quand on a lu cet
immense volume d'hypothèses sur la pluralité des mondes éternels,
savez-vous à quoi l'on retourne pour se délasser d'une telle
lecture?... Aux historiettes astronomiques de Fontenelle et aux
gasconnades de Cyrano de Bergerac.
DONOSO CORTÈS[6]

I
Intellectuellement, c'est une frégate à la mer que la publication de
ces œuvres[7] de Donoso Cortès. Chargés de vérité et, pour ainsi
parler, pavoisés des couleurs d'un grand talent, dont le caractère est
l'éclat, ces trois volumes, comme le vaisseau que montait l'aïeul de
Cortès pour aller à la conquête d'un monde, s'en vont à la conquête
des âmes, qui sont aussi des mondes, et peut-être plus difficiles à
conquérir... Quelle que soit leur destinée, c'est un service rendu à
l'Église que d'avoir pensé à les traduire et à les publier dans cette
langue française qui n'est pas seulement, comme on l'a dit, la langue
de la diplomatie et de la philosophie, mais qui est plus qu'une autre
la langue de la propagation et de la foi.

Donoso Cortès, marquis de Valdegamas, est un des écrivains


catholiques les plus éminents de ces dernières années. Il a laissé,
presque dès son début, des traces trop vives et trop profondes dans
l'opinion contemporaine pour qu'on pût oublier de réunir les écrits
dus à cette plume brillante que la mort a si tôt brisée, et qu'il eût
brisée lui-même s'il avait vécu davantage, tant elle satisfaisait peu
son âme sainte! D'un bien autre génie que Silvio Pellico, mais d'une
humilité non moins touchante, le marquis de Valdegamas avait plus
de confiance dans une dizaine de chapelet, dite d'un cœur fervent,
que dans tous les étalages de la pensée. Et il avait raison! Mais ses
amis qui le publient aujourd'hui n'ont pas tort pourtant de le publier.
Ils savent que Dieu, pour traverser les cœurs, met dans nos carquois
toutes sortes de flèches, et que la flèche du talent pénètre encore
après les plus perçantes,—celles de la prière et de la charité!

Du reste, catholiques avant tout, ils n'ont point publié les œuvres
complètes du marquis de Valdegamas. Ils ont laissé la littérature de
l'homme exclusivement littéraire (Donoso Cortès l'avait été un
moment), et ils n'ont pris dans ses travaux que ce que le
catholicisme a animé de son inspiration toute-puissante. Ils se sont
donc strictement renfermés dans l'œuvre catholique de Donoso,
trouvant le reste de peu de signifiance, même pour sa gloire. En
cela, ils ont sainement jugé.

Donoso Cortès, cet écrivain incontestablement supérieur par un


talent qui touche au premier ordre, cet orateur qui a poussé ces
deux ou trois discours dont l'air que nous avons autour de la tête
vibre encore, l'illustre Donoso Cortès, disons-le brutalement, ne
serait rien sans le catholicisme, et ce n'est pas, certes! pour
l'abaisser que nous disons cela. Resté l'homme des pensées du
temps, il ne se serait jamais beaucoup élevé au-dessus de la
fonction vulgaire d'un médiocre littérateur. Piètre destinée! Mais,
avec le catholicisme, son génie a commencé dans son âme. C'est le
catholicisme qui lui a créé une pensée. Il a reçu la langue de feu... Il
ne l'avait pas!

II
Et la preuve, elle est ici, dans ces œuvres qui ne sont pas complètes,
mais choisies. Trop facile à donner si nous examinions l'intégralité
des écrits de Donoso Cortès, cette preuve ne brille que mieux en ces
œuvres partielles, réunies par ces deux sœurs pieuses, l'admiration
et l'amitié. Les éditeurs de Donoso ont publié, avec son ouvrage
principal: l'Essai sur le catholicisme, le libéralisme et le socialisme,
qui a fixé sa gloire et qui la gardera, beaucoup de discours, d'articles
de journaux, de lettres datées de diverses époques, et il en est
plusieurs de celles-là où, comme tant de ses contemporains, Donoso
Cortès, trop fort d'esprit pour n'avoir pas le respect du catholicisme,
reculait encore devant la pratique, cet effroi des lâches, sans laquelle
il est impossible au penseur le plus fort de se justifier tout son
respect.

Eh bien, quoique tous ces écrits portent, à des degrés différents, la


marque de ce catholicisme qui finit par s'emparer complètement de
Donoso Cortès et le fit naître à force de le féconder, il saute aux
yeux que les plus faibles catholiquement de ces écrits sont, au point
de vue du talent seul, d'une faiblesse plus que relative!... On voit,
clair comme le jour, à travers ces écrits, ce qu'aurait été toute sa vie
Donoso Cortès sans ce catholicisme maîtrisant et transfigurateur qui
fut le ciel pour son talent. Il serait, sans nul doute, resté, en toutes
choses, l'homme de l'incroyable jugement sur Talleyrand de La
France en 1842, et cet homme était un rhéteur. Il n'y a qu'un
rhéteur, en effet, et un rhéteur de la pire espèce, qui puisse
comparer Napoléon et Talleyrand, et mettre Talleyrand au-dessus de
Napoléon!

Oui! cette tache de la rhétorique se serait étendue sur toute la


pensée, et la taie eût bientôt couvert l'œil. Cet esprit, né brillant,
n'aurait bientôt plus résisté à la tentation d'une seule antithèse. La
solidité ne serait pas venue, ni la force simple ni la sincérité. Le
talent de nature aurait grandi, plus ou moins mensonge ou caresse;
le talent de grâce n'aurait point paru. Nous aurions eu dans tout son
développement le rhéteur qui est au fond—tout au fond—du talent
de Donoso Cortès; car il y est, le rhéteur,—plus ou moins doué, plus
ou moins puissant, ce n'est pas la question!—mais il y est. Malgré la
grâce du catholicisme, la Critique l'y voit encore sous cette grâce qui
a tout dompté.
Donoso Cortès est du pays des grands rhéteurs, Sénèque, Lucain et
Gongora. Il l'est aussi, même quand il croit et veut le moins l'être,
même quand il insulte la beauté littéraire: «J'ai eu—dit-il dans une
lettre à Montalembert—le fanatisme de l'expression, le fanatisme de
la beauté dans les formes, et ce fanatisme est passé... Je dédaigne
plutôt que je n'admire ce talent qui est plus une maladie de nerfs
qu'un talent de l'esprit...» ce qui est assez insolent et assez faux, par
parenthèse. Et au moment même où il écrit cela, sans transition et
comme pour se punir, il ajoute ce mot de rhéteur inconséquent, de
rhéteur incorrigible, qui tout à coup reparaît: «Les formes d'une
lettre ne sont ni littéraires ni belles». Misérable axiome de
rhétorique, non moins faux!

Et pourquoi ne seraient-elles pas belles?... Mais laissons là ces


dédains factices qui n'ont pas le droit d'exister. Le catholicisme, cette
source sublime d'inspiration, a donné à Donoso Cortès une assez
belle forme pour qu'il ne puisse la dédaigner sans affectation ou
sans injustice, et il ne la lui a donnée qu'à la condition d'élever,
d'épurer, de grandir toutes les forces de sa pensée; car la pensée et
la forme ne se séparent pas. Elles sont congénères et
consubstantielles. L'homme ne se dédouble pas. Il y périrait. Les
rhéteurs seuls ont pu inventer cette platitude du vêtement et du
corps, pour dire le style et la pensée. Mais où cela s'est-il vu? Pour
notre part, nous ne croyons pas plus à l'écrivain sans pensée qu'au
penseur sans style... Kant lui-même a du style, quand, par rareté, il
a raison.

III
Donoso Cortès, qui a toujours raison quand il est entièrement
catholique, est donc un grand écrivain dont la Critique est appelée,
aujourd'hui qu'on publie ses œuvres, à dire les défauts et leur
étendue, les qualités et leur limite. Son mérite le plus net, à nos
yeux, le plus grand honneur de sa pensée, c'est d'avoir ajouté à une
preuve infinie; c'est, après tant de penseurs et d'apologistes qui,
depuis dix-huit cents ans, ont dévoilé tous les côtés de la vérité
chrétienne, d'avoir montré, à son tour, dans cette vérité, des côtés
que le monde ne voyait pas; c'est, enfin, d'avoir, sur la chute, sur le
mal, sur la guerre, sur la société domestique et politique, été
nouveau après le comte de Maistre et le vicomte de Bonald, ces
imposants derniers venus! La vérité a des fonds de sac étonnants et
inépuisables. On croit que c'est la fin, et voilà que tout recommence,
sans se répéter!

Ce que le comte de Maistre et le vicomte de Bonald firent contre les


erreurs de leur temps, le marquis de Valdegamas l'a fait contre les
erreurs du sien, et il l'a fait avec des qualités tout à la fois
semblables aux leurs et différentes... L'un (le comte de Maistre) était
un grand esprit intuitif; l'autre (le vicomte de Bonald) un grand
esprit d'enchaînement. Donoso Cortès a bien parfois l'aperçu de
Joseph de Maistre, mais cet aperçu n'arrive pas chez lui, comme
chez de Maistre, pareil à un trait de lumière qui part du fond de la
pensée, au rayon visuel qui jaillit du centre de l'œil. C'est lui plutôt,
Donoso, qui arrive à l'aperçu comme à une lumière en dehors de sa
pensée, et, à force d'aller vers elle, de raisonnement en
raisonnement.

On pourrait dire de Donoso Cortès qu'il a de l'aperçu par


développement, tandis que pour de Maistre l'aperçu point d'abord et
le développement vient ensuite, s'il en est besoin. Pour cette raison
même, Donoso Cortès a certainement autant de logique que de
Bonald. Il y a plus: on peut affirmer que c'est la logique, entre
toutes les puissances de son esprit, qui lui fait sa supériorité
absolue. Il en a les formes rigides et souples, l'enthymème,
l'énumération, le sorite. C'est toujours enfin de la pure logique qu'il
tire, lorsqu'elle est belle, toute la beauté de sa pensée. Soit donc
qu'il fasse acte d'écrivain à tête reposée ou d'orateur s'exprimant
dans un parlement, Donoso Cortès est partout et surtout un
formidable logicien, et tellement logicien qu'il ne craint pas d'être
scolastique par la forme, car il a assez d'expression à son service
pour ne jamais paraître sec.

Il a, en effet, les dons du génie espagnol. Il en a la solennité, qui est


l'emphase contenue. Il en a la pompe, l'harmonie, le nombre, la
plénitude, la sonorité. C'est un large cours de pensées que ses
pensées, enchaînées les unes aux autres comme les flots aux flots,
mais auxquelles il faut de la place. Il faut à Donoso Cortès de
l'espace pour rouler son fleuve! Il n'a pas le monosyllabe, la paillette
qui fait du fleuve un Pactole, la pointe acérée et étincelante, ce clou
d'or, quand il n'est pas de diamant, qu'avait Joseph de Maistre, et
qu'il fichait si bien, de sa main spirituelle, entre les blocs carrés et
lisses de son style au ciment romain.

Le style d'un homme, lorsque cet homme n'est pas assez fort pour le
faire avec sa seule manière de sentir, a ses origines. Pascal, par
exemple, c'est Montaigne, plus la manière de sentir de Pascal, et
cette manière, c'était l'épouvante, l'effarement, le cabrement devant
l'abîme. L'origine du style de Donoso Cortès est saint Augustin dans
ses Confessions. Saint Augustin l'attire par sa tendresse, la grande
qualité de son esprit et de son âme. Il l'attire aussi par son défaut
peut-être, car saint Augustin, sous les magnificences de son génie,
comme Donoso Cortès sous le sien, cache son atome de rhéteur.

IV
Tel nous trouvons en ces trois volumes le talent du marquis de
Valdegamas. Plus oratoire que littéraire, Donoso Cortès a, même
lorsqu'il s'efforce d'être didactique, comme dans son Essai sur le
catholicisme, le libéralisme et le socialisme, les aspirations, les
apostrophes, le mouvement et le redoublement antithétique. Il a de
l'orateur: Il doit avoir lu immensément les sermonnaires. Il a les
grands mots oratoires qui une fois dits ne s'oublient plus: «Ou un
seul homme—dit-il un jour—suffirait pour sauver la société: cet
homme n'existe pas; ou, s'il existe, Dieu dissout pour lui un peu de
poison dans les airs!» Un autre jour: «Dieu a fait la chair pour la
pourriture, et le couteau pour la chair pourrie.» Et encore: «Où que
l'homme porte ses pas, il la rencontre (la douleur), statue muette et
en larmes, toujours devant lui!» Rappelez-vous ce qu'il dit une fois
de Sainte-Hélène: «Napoléon, le maître du monde, devait mourir
séparé du monde par un fossé dans lequel coulerait l'Océan.» Il
parle quelque part de je ne sais quelle doctrine indigne de la
majesté de l'absurde.

Un peu plus, il serait déclamateur; mais il s'arrête à temps et le goût


est sauvé. Du reste, rarement fin, et ceci l'honore... La finesse de
l'esprit n'est souvent qu'une ressource de sa lâcheté. Donoso est le
courage même. Il a la foi de ce qu'il dit, et il ne se baisserait pas
d'une ligne pour ramasser tout un monde de popularité si Dieu le
mettait à ses pieds.

C'est le contraire d'un autre éclatant, de Chateaubriand, sur lequel il


l'emporte par la pureté, le calme et la beauté de l'âme, s'il ne
l'emporte pas par la beauté de son génie. Il se soucie peu de la
gloire. «Je ne veux pas que mon nom résonne—dit-il dans une de
ses lettres;—je ne veux pas que les échos le répètent et qu'il
retentisse sur les montagnes. Il n'est pas en mon pouvoir
d'empêcher mes adversaires de le prononcer, mais je suis résolu à
empêcher mes amis de le faire, et c'est le but de cette lettre.»

Et lorsqu'il écrit cela il est très vrai. Il est conséquent à ce qu'on


trouve partout, à mainte page de ses œuvres: «L'idéal de la vie,—
dit-il,—c'est la vie monastique. Ceux qui prient pour le monde font
plus que ceux qui combattent.» Et, en effet, lui, l'ambassadeur qui
n'a jamais fait comme Chateaubriand, ce fat d'affaires, ce porteur
d'empire sur le bout du doigt, ennuyé à la mort si on l'en croyait et
lassé de ce faucon qui pèse si peu au poing du génie, il allait,
lorsque la tombe le prit, quitter simplement ses costumes de palais,
qu'il n'appelle nulle part des guenilles, et revêtir une soutane. Dieu
ne le permit point; il lui gardait un autre autel à desservir. Il l'appela
et en fit son prêtre... pour l'éternité, dans les cieux!

V
Nous avons dit que l'ouvrage principal de Donoso Cortès, le seul qui
lui gardera dans la postérité cette gloire à laquelle il ne tint point
durant sa vie, était son Essai sur le catholicisme, le libéralisme et le
socialisme, et c'est même le seul ouvrage régulièrement composé
qu'il ait laissé parmi ses œuvres. Turbulences dans un temps
turbulent, cris éloquents poussés sous la pression des circonstances,
les autres écrits de Donoso Cortès, discours, articles de journaux ou
lettres, ne sont pas des livres à proprement parler et dont la Critique
puisse donner l'anatomie.

On les lira encore quelque temps, puis ils tomberont des mains, ne
laissant dans les esprits d'autre impression que l'impression du bruit
qu'ils firent, et ce sera bientôt effacé. Les journalistes et les orateurs
sont plus mortels que les autres hommes. Ils se résolvent mieux et
plus vite en poussière. Voix de la bouche, voix de la plume, qui se
sont fiées à l'air, à cette petite bouffée de vent dans laquelle elles
ont parlé... Le vent ne les trahit pas, et il les emporte! Quoiqu'il ait
eu, comme orateur, ses deux à trois moments sublimes, Donoso
Cortès, ni dans le journal ni à la tribune, n'a été un de ces voyants à
distance, qu'on nous passe le mot! un de ces prophètes de longueur
qu'il faut forcément être si, comme orateur ou comme journaliste, on
a la prétention, que je trouve un peu forte, de ne pas mourir.

Dans ses Lettres sur la France en 1851, il parcourt, jour par jour, le
cercle que toutes les intelligences de ce temps, quand elles n'étaient
pas folles, ont pu parcourir; mais je ne vois rien là de prédominant
et de supérieur.
Les événements lui donnent dans les yeux de leur impalpable cendre
de chaque jour et font ciller ses mélancoliques paupières, qui n'ont
pas l'immobilité de celles de l'aigle. Lorsque ailleurs, je crois, sur
cette immense et noire tenture de mort dans laquelle il voit l'Europe
enveloppée (et qui l'est... peut-être), il se mêle de découper de
petites prophéties spéciales, il ne réussit pas. Il manque son coup:
«Si la Russie—dit-il—entre en Allemagne, il n'y a plus qu'à accepter,
en y ajoutant le mot de Napoléon: L'Europe sera républicaine ou
cosaque... si elle n'est catholique», et pourtant rien de tout cela
n'est arrivé. La peur, comme l'espoir, voit plus grand que nature.

Le vieux monde s'est rassis sur ses vieux fondements, et ç'a été
tout. Évidemment, la gloire vraie de Donoso Cortès n'est point dans
des perspicacités de cet ordre. Elle est ailleurs, et c'est dans son
Essai sur le catholicisme qu'il faut la chercher.

Elle est aussi dans cette philosophie de l'histoire qu'on trouve, dès
1849, dans la lettre, datée de Berlin, à Montalembert, et qui est
d'ailleurs la vue génératrice de toutes les vérités de l'Essai, lesquelles
sont nombreuses. Cette vue exprimée et développée déjà par
Donoso Cortès, et qu'il démontre, à savoir: le triomphe naturel du
mal sur le bien, et le triomphe surnaturel de Dieu sur le mal, par le
moyen d'une action directe personnelle et souveraine, n'avait jamais
été formulée avec cette plénitude et cette vigueur. C'est dans la
radieuse clarté de cette vue complète que Donoso écrivit l'Essai, qui
est tout ensemble la plus profonde apologie du dogme catholique et
une attaque contre les doctrines contemporaines dont le but est
d'abattre ce dogme et de le ruiner.

Pour Donoso Cortès comme pour Blanc-Saint-Bonnet (une autre


gloire catholique qui se fait présentement devant Dieu, et qui, un
jour, saisira l'attention des hommes), la théologie est la seule science
qui explique l'histoire, qui la prépare et puisse la gouverner, et il le
prouva en en appliquant les notions à tous les problèmes soulevés
dans son livre. Là il déposa tout son effort, toute sa force, et sa vie
presque. Il mourut, en effet, quelque temps après qu'il eut fini ce
livre, qu'on mettra désormais entre les Soirées de Saint-Pétersbourg
et les Recherches philosophiques de l'auteur de la Législation
primitive;—à côté, mais un peu au-dessous des Soirées; à côté des
Recherches, mais aussi un peu au-dessus.

Avec son seul livre de l'Essai, le marquis de Valdegamas s'est placé


entre le comte de Maistre et le vicomte de Bonald, qu'on pourrait
presque appeler les Pères laïques de l'Église romaine. On s'en
souvient, ils avaient, au XVIIIe siècle, mis partout leurs trois dieux:
Voltaire, Rousseau et Franklin, qu'ils appelaient le Flambeau de
l'humanité, dans le style du temps, sérieux et comique, déclamatoire
et plat.

Nous, catholiques du XIXe siècle, nous n'avions à opposer aux trois


colosses de la philosophie que deux hommes de hauteur, qui en
valaient bien trois, il est vrai: de Maistre et de Bonald; mais il nous
manquait le troisième. A présent, nous l'avons, et ce sera Donoso
Cortès.

Dans cette réplique d'un siècle à un autre par ses plus grands
hommes, le comte de Maistre,—avec son esprit merveilleux, si
aristocratique, si français, et ce don de plaisanterie charmante qui
était comme la fleur de son profond génie,—le comte de Maistre
tient naturellement la place de Voltaire, et c'est bien le Voltaire du
catholicisme, en effet. Bonald, qui en est le Montesquieu, Bonald,
éloquent à force de dialectique, s'y oppose vivement à Rousseau, et,
chose singulière et piquante! Donoso Cortès, du pays du Cid et de
sainte Thérèse, Donoso Cortès, qui a mis toutes les sciences de la
terre aux pieds de la théologie, y fait vis-à-vis et contraste au
naturaliste Franklin!

VI
Les œuvres choisies de Donoso Cortès sont précédées d'une
introduction de Louis Veuillot, qui, comme il nous l'apprend, fut l'ami
du marquis de Valdegamas. Cette introduction est de la placidité
pleine de force qu'ont les chrétiens quand ils regardent deux choses
tristes:—le monde et un tombeau. Elle n'a point de chétive petite
mélancolie.

Le monde ne sut point assez ce que valait Donoso Cortès, et Veuillot


l'a dit tranquillement, sans rien surfaire. Au premier rang de ce
monde par les titres et les relations, Donoso Cortès, marquis de
Valdegamas, n'y exerça pas toute l'influence à laquelle, de talent et
d'âme, il avait droit, et la faute en fut justement au monde de ce
temps, haïsseur de toute vigueur et de toute vérité complète. Il
fallait à un homme comme Donoso Cortès l'époque de Ximenès, et
Ximenès même pour ministre. Il ne l'eut point, et, comme tant
d'autres, il vint trop tard. Mais n'admirez-vous pas cette louange
amère? Le plus grand honneur qu'on puisse faire aux hommes du
XIXe siècle, c'est de supposer qu'ils n'en sont pas!
SAISSET[8]

I
L'Essai de philosophie religieuse d'Émile Saisset veut à toute force
être modeste. C'est une composition très travaillée en modestie. On
s'attendait peu à ce ton, agréable du reste, et convenable surtout,
de la part de Saisset, un des diacres de Cousin, qui proclamait, il y a
peu d'années, que les philosophes «étaient désormais les seuls
prêtres de l'avenir,» et cela avec le contentement fastueux d'un
homme qui en tenait sous clef tout un petit séminaire. Saisset,
professeur, et, si je ne me trompe, suppléant de Cousin, lequel, lui, a
donné sa démission de philosophe entre les mains des dames et est
entré dans les pages de madame de Longueville, Saisset a baissé
infiniment de note depuis le temps où il se croyait un prêtre et, qui
sait? peut-être un évêque des temps futurs. Sa religion de l'avenir lui
paraît, en ce moment, fort menacée, et son livre est un cri d'alarme;
mais un cri d'alarme discrètement poussé, car tout est discret dans
Saisset: le ton, le talent, et même la peur.

Il a peur, en effet. Et il y a de quoi. La philosophie qu'il adore (sic)


est cernée et va mourir un de ces jours, non pas, comme Constantin
Paléologue, au centre d'un monceau d'ennemis circulairement
immolés autour d'elle, car la philosophie de Saisset n'a jamais tué
personne: elle n'est meurtrière que de vérité; mais elle va mourir au
milieu d'ennemis chaque jour plus nombreux, plus prompts aux
coups et plus puissants... Parmi eux, bien entendu, le catholicisme
est là qui la presse, et non pas seulement le catholicisme farouche,
haineux, théocratique et rétrograde, que hait modestement Saisset,
mais le doux, le rationnel, le tolérant, que les prêtres des temps
futurs souffrent auprès d'eux en attendant leur propre ordination
définitive. Il est assez simple et assez naturel que le catholicisme soit
contre la philosophie, qui veut lui succéder. Mais voici plus étonnant
et plus terrible. La philosophie est attaquée par la philosophie elle-
même. Ses parricides entrailles se retournent contre elle. Tu quoque,
fili! Elle est frappée par son fils Brutus. Le fils Brutus de la
philosophie est le panthéisme, et ce fils Brutus mérite bien son nom.
Il est brute et brutal.

Et, de fait, le panthéisme, vous dira Émile Saisset, est en train de


devenir tout à l'heure la philosophie universelle de l'Europe. Que
l'Europe le sache ou l'ignore, qu'elle en soit consciente ou
inconsciente, elle est en lui, il est en elle, il est partout! Il est dans
les penseurs, il est dans les artistes, il est même dans les femmes,
qui croient à la substance et plaisantent... panthéistiquement! La
France fut assez jeune, dans le temps que Cousin n'était pas encore
dans les pages de madame de Longueville et commissionnait pour le
compte de la philosophie française, la France fut assez naïve (ce
n'est pas là pourtant son habitude, mais c'était la France
philosophique, il est vrai,) pour accepter comme une merveille
exotique les germes de l'hegelianisme rapportés pieusement dans le
chapeau ou sous le chapeau de Cousin, et cette fleur a donné ses
fruits. Qui a goûté du Proudhon, du Taine, du Renan, du Vacherot,
les connaît, ces fruits germaniques, cultivés par des mains françaises
sur un sol français. Ce n'est pas bon, mais c'est demandé, et la
philosophie telle que l'enseigne Saisset commence à ne plus placer
ses produits. Ils paraissent insuffisants, fades et même fadasses, aux
goûts développés et à la fureur d'un temps dépravé. Il y a des
choses qui font trembler Saisset. L'accroissement de la personnalité
qui s'en va monstrueux, la rage universelle de jouir, et tout de suite
encore! enfin l'activité de l'esprit aiguillonnée, exaspérée par cette
rage de jouir, voilà ce que ne saurait diminuer, apaiser ou contenir la
philosophie, un peu vieillotte, maintenant, pour ce faire, qu'on
appelle proprement la philosophie française, celle-là qui sortit de
Descartes,—lequel, lui, ne sut jamais sortir de lui-même!—qui fit un
jour sa grande fredaine de Locke, mais qui s'en est repentie quand
elle fut sur l'âge, plus morale en cela qu'une de ses amies, la
grand'mère de Béranger.

Eh bien, cette philosophie est-elle irrémédiablement finie? Doit-elle


définitivement céder la place, l'influence et l'empire, au catholicisme,
qui nous ramènera au moyen âge ou au panthéisme, qui nous
amènera un âge comme l'histoire n'en a pas encore vu? Car la
question se débat, selon Saisset, entre ces deux alternatives: «Il n'y
a que deux espèces de penseurs conséquents,—dit-il textuellement à
la page XXV de son introduction:—ceux qui nient la raison, la science
et le progrès et veulent le retour de la théocratie du moyen âge, et
ceux qui veulent une reconstitution radicale de la société et de la vie
humaine.» Pour lesquels nous prononcerons-nous?...

Après ces paroles et la question ainsi posée, qui ne croirait que


Saisset a choisi? Qui ne croirait qu'il est un de ces radicaux
courageux, un de ces panthéistes qui semblent les progressistes
réels en philosophie, puisqu'ils sont les derniers venus? Et
cependant, non! il ne l'est pas. Loin de choisir, il se dérobe. Bien loin
d'être une déclaration de panthéisme, le livre est, au contraire, une
discussion en forme contre le panthéisme et une doctrine élevée à
côté pour échapper aux conclusions envahissantes de ce fléau qui
s'étend toujours. Entre les théocrates du moyen âge et les terribles
séculiers de l'avenir, qui a donc pu retenir Saisset et lui faire tracer
une tangente par laquelle il se sauve des uns et des autres? Cela est
curieux, mais cela doit être certainement la théocratie à son usage,
cette théocratie philosophique qui n'est pas rétrograde, celle-là, et
qu'il a rêvée pour lui et pour ses amis. Il ne veut pas manquer sa
prêtrise. Il ne lâche pas sa part de troupeau, et son livre, intitulé
Essai de Philosophie religieuse[9], n'a pas d'autre sens que celui-là,
sous ses formes d'une simplicité piperesse et d'une modestie qui
prouve qu'on n'a plus la puissance, car l'humiliation n'est pas
l'humilité!

II
Mais, si Saisset a vu très juste dans les circonstances
contemporaines, et si la question morale et intellectuelle du monde
doit s'agiter entre les conséquents du catholicisme et les
conséquents du panthéisme, a-t-il vu également juste en croyant
possible d'établir, ou, pour parler aussi modestement que lui, de
pressentir une troisième solution à introduire, en catimini, sous les
regards de l'opinion, avec des patelinages de plume qui montrent au
moins de la souplesse dans son talent? Si la question philosophique
du temps présent est, comme il l'a dit et comme je le crois, la
question de la personnalité divine; si, au terme où est arrivé l'esprit
humain, il faut, de rigueur, être pour l'homme-Dieu tel que la religion
de Jésus-Christ nous l'enseigne, ou pour le Dieu-homme tel que
l'établit Hegel, Saisset, qui veut bien du sentiment chrétien, mais qui
ne veut pas de la religion chrétienne, et qui, non plus, ne veut pas
du panthéisme, qu'il hait comme un voleur d'héritage parce qu'il le
priverait de la succession sur laquelle il a compté, Saisset, à qui je
ne demanderai pas plus qu'il ne peut me donner, a-t-il fait, du
moins, dans son Essai de philosophie religieuse, pour le compte de
la personnalité divine, quelque découverte qui fasse avancer cette
question?

Je viens de lire cette longue méditation cartésienne, faite les yeux


fermés et les mains jointes avec les airs de recueillement d'un
philosophe en oraison, dans l'in pace de la conscience, dans le
silence profond de la petite Trappe psychologique que tout
philosophe porte en soi pour y faire des retraites édifiantes de temps
en temps et s'y nettoyer l'entendement, et, je l'avoue, je n'y ai rien
trouvé qui m'éclairât d'un jour inconnu et fécond la personnalité
divine que nous autres catholiques nous savons éclairer du jour
surnaturel de la foi.

Et il y a plus! je n'ai trouvé, dans cet Essai de philosophie religieuse,


ni philosophie ni religion, car le déisme n'est pas plus une religion
que le spiritualisme n'est une philosophie, et le mot même d'essai
n'est pas plus vrai que le reste avec sa modestie, car un essai
suppose qu'on s'efforce à dire une chose neuve, et l'auteur en redit
une vieille dont nous sommes blasés, tant nous la connaissons!

En effet, Saisset, dans ce livre nouveau, quoiqu'il soit imité de


Descartes, est éternellement le Saisset de la Revue des Deux
Mondes et des Essais sur la religion et la philosophie au XIXe siècle.
Les philosophes ont bien parfois des velléités de transformation,
mais ils ne réussissent guères à s'enlever de la glu d'idées dans
laquelle ils ont été pris une fois, et leur pensée y reste prise.
L'englument éclectique n'a point manqué à Saisset. Il ne s'en retirera
jamais. L'éclectique qu'il fut dans sa jeunesse, il l'est encore.
Philosophiquement, comme tous ses pareils, les éclectiques du
commencement du siècle, faits par Cousin à son image, il a toujours
eu un petit bagage d'idées fort léger. Comme les éclectiques, ces
emprunteurs à tout le monde, il les doit, ses idées, à Descartes, à
Leibnitz ou à Reid, et cela s'appelle la progression des êtres, le grand
optimisme, la liberté humaine, la Providence et l'étude des faits de
conscience; et voilà la valise faite de Saisset et de ces messieurs!

Eh bien, aujourd'hui que cette philosophie court-vêtue et en souliers


plats, et fort plats,—comme la Perrette, portant sur sa tête son pot
au lait, dans la fable,—aujourd'hui que cette philosophie a une peur
blême pour ce pot au lait qui va tomber peut-être, Saisset a-t-il au
moins ajouté quelque chose à son poids pour en assurer l'équilibre?
Y a-t-il mis le poids d'une idée de plus, et n'est-ce pas sans cesse le
même ballonnage de spiritualiste et de providentiel, qui ne leste
rien, n'assure rien et titube toujours?...
Son livre est divisé en deux parties: la première est l'histoire
discursive et critique des philosophes antérieurs et contemporains et
de leurs systèmes: Descartes, Malebranche, Spinoza, Newton,
Leibnitz, Kant, Fichte, Schelling et Hegel, et, dans un temps où la
philosophie n'est plus que l'histoire de la philosophie, cette partie du
livre, dans laquelle il y a l'habitude des matières traitées qui singe
assez bien le talent, se recommande par l'intérêt d'une discussion
menée grand train et avec aisance; mais, d'importance de sujet, elle
est bien inférieure à cette seconde partie où l'esprit s'attend à
trouver, contre toutes les erreurs et les extravagances signalées par
l'auteur dans toutes les philosophies, un boulevard doctrinal solide,
et s'achoppe assez tristement contre ces infiniment petits
philosophiques: le déisme de la psychologie et ses conséquences
inductives et probables,—ce déisme dont Bossuet disait, avec la
péremptoire autorité de sa parole, «qu'il n'est qu'un athéisme
déguisé»! Avouez que c'est là une puissante manière de fortifier aux
yeux des hommes la personnalité de Dieu.

Telle est pourtant la théorie d'Émile Saisset.

Ce n'est pas même une théorie. Ce sont des affirmations peu carrées
et peu appuyées, mais rondes plutôt et glissantes, de ces inductions
données cent fois par l'école cartésienne tout entière, cette école du
moi qui n'a jamais su jeter de pont d'elle à Dieu et dont l'auteur de
l'Essai d'une philosophie religieuse a répété, sans les varier, les
termes connus. Ce n'est ni plus ni moins qu'un petit catéchisme
cartésien à l'usage des faibles qui ne veulent pas devenir forts, car la
force, c'est une témérité pour les prudents, et la force serait, sur
cette question de Dieu, de s'élever plus haut qu'une philosophie qui
la pose, l'agite, mais n'a jamais pu la résoudre.

Certes! oui, Saisset a bien raison d'être modeste. Quand il l'est, on


peut le prendre au mot. Sans originalité d'aucune sorte, trivial même
dans le faux, par exemple dans la question des religions, qui ne
sont, d'après lui, que des amusettes et des symboles, l'œuvre de
Saisset n'ose rien de dogmatique et de réellement décisif sur la
personnalité divine, d'abord parce que le déisme pur ne le permet
pas, et ensuite parce que, sur cette question de Dieu, l'Institut ne se
soucie pas qu'on dépasse la ligne circonspecte d'une haute
convenance sociale. Or, Saisset est un déiste qui vit toujours, de
pensée, de désir et d'âme, en la présence de l'Institut.

III
Mais, si le livre de Saisset est d'une si profonde nullité dans sa partie
affirmative, nous serons assez juste pour revenir et pour insister sur
la valeur de la partie négative ou critique de son ouvrage. Cette
partie négative, d'ailleurs, est toujours la meilleure chez tous les
philosophes, ce qui, par parenthèse, est un cruel arrêt, implicitement
porté par les faits, contre la philosophie elle-même. Les philosophes
ne sont vraiment forts que les uns contre les autres. Sans leurs
erreurs mutuelles, que seraient-ils?...

Saisset, qui n'a jamais été une de ces supériorités qui ont, de génie,
le droit de haute et basse justice sur les systèmes couverts du porte-
respect des grands noms, Saisset, qui ne fut jamais rien de
beaucoup plus qu'un joli sujet en philosophie, n'en a pas moins
exercé la magistrature du bon sens et de la raison, en maint endroit
de ses critiques, contre des hommes de l'imposance d'un Leibnitz,
d'un Descartes, d'un Kant, d'un Spinoza. Je sais bien qu'en relevant
l'erreur il reste courbé devant celui qui l'a produite, et je reconnais là
le joli sujet dont je parlais tout à l'heure, respectueux pour ses
maîtres et obstiné au respect pour eux, malgré leurs plus honteuses
et leurs plus dangereuses folies.

Un esprit plus vigoureux que celui de Saisset ne vénérerait pas la


force jusque dans l'abus qu'on fait d'elle, un bon sens plus fier
n'aurait pas de ces attitudes devant les gauchissements du génie ou
ses crimes,—car les fautes intellectuelles d'un homme investi de
facultés transcendantes peuvent aller jusque-là; mais il faut se
rappeler que Saisset est professeur, et je nomme ce respect déplacé
le mal de l'école. Un professeur n'a pas la recherche libre de la
philosophie. Il est professeur avant d'être philosophe. S'il était plus
philosophe, il ne serait pas professeur... De plus, quand on vit en
intimité d'étude avec les grands esprits philosophiques, avec ces
grands cerveaux, tous fausseurs ou corrupteurs, plus ou moins, de la
tête humaine, si on leur arrache par la réflexion l'intégrité de sa
pensée, on leur laisse de sa dignité par l'admiration qu'on ne leur
arrache pas, et c'est ce qui est arrivé à Saisset quand il se sépare
des sophismes de ses maîtres et qu'il a le courage de les montrer.
Ainsi pour Spinoza, par exemple, dont il voit très bien le vice radical
et profond, le vice irrémissible, il reste sans conclure par le mépris
mérité avec ce fakir hollandais et juif beaucoup trop vanté, né de la
kabbale et du gnosticisme, dans un coin, et qui ne fut jamais que le
génie obscur de l'abstraction et de la géométrie, dévoyé dans l'étude
de l'homme. L'enthousiasme du mandarin, et je dirai plus, de
l'écolier, est ici plus fort que le bon sens primitif, et met un défaut de
proportion des plus choquants entre la critique qu'on s'est permise
et l'admiration qu'on garde encore...

Eh bien, cela est inférieur! Il est inférieur aussi, après avoir conclu
au particulier dans chacune de ces biographies intellectuelles, de
n'avoir pas su conclure au général et, après avoir fait passer
philosophes et systèmes par le creuset de l'analyse, de n'avoir pas
jaugé d'un dernier regard la puissance en soi de la philosophie. Otez,
en effet, les vérités indémontrables et nécessaires à la vie et à la
pensée humaines qu'on savait avant les philosophes et auxquelles ils
n'ont pas donné un degré de certitude de plus,—le nombre infini de
leurs sophismes laborieux,—les forces d'Hercule perdues par eux
pour saisir le faux ou le vide,—le mal social de leurs doctrines, qui
n'ont pas même besoin d'être grandes pour produire les plus grands
maux,—ôtez cela, après l'avoir pesé, et dites-moi ce qui reste de
tous ces philosophes et de toutes ces philosophies, même de ceux
ou de celles qui paraissent le plus des colosses!
Welcome to our website – the perfect destination for book lovers and
knowledge seekers. We believe that every book holds a new world,
offering opportunities for learning, discovery, and personal growth.
That’s why we are dedicated to bringing you a diverse collection of
books, ranging from classic literature and specialized publications to
self-development guides and children's books.

More than just a book-buying platform, we strive to be a bridge


connecting you with timeless cultural and intellectual values. With an
elegant, user-friendly interface and a smart search system, you can
quickly find the books that best suit your interests. Additionally,
our special promotions and home delivery services help you save time
and fully enjoy the joy of reading.

Join us on a journey of knowledge exploration, passion nurturing, and


personal growth every day!

ebookbell.com

You might also like